Skip to content

Commit 40a5958

Browse files
committed
refactor(block): add retries on SetFinal
1 parent bc6a0b1 commit 40a5958

5 files changed

Lines changed: 42 additions & 29 deletions

File tree

apps/evm/single/cmd/rollback.go

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -93,12 +93,12 @@ func NewRollbackCmd() *cobra.Command {
9393
}
9494

9595
if err := headerStore.Start(goCtx); err != nil {
96-
return err
96+
return fmt.Errorf("failed to start header store: %w", err)
9797
}
9898
defer headerStore.Stop(goCtx)
9999

100100
if err := dataStore.Start(goCtx); err != nil {
101-
return err
101+
return fmt.Errorf("failed to start data store: %w", err)
102102
}
103103
defer dataStore.Stop(goCtx)
104104

block/internal/common/retry.go

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
package common
2+
3+
import "time"
4+
5+
// MaxRetriesBeforeHalt is the maximum number of retries before halting.
6+
const MaxRetriesBeforeHalt = 3
7+
8+
// MaxRetriesTimeout is the maximum time to wait before halting.
9+
const MaxRetriesTimeout = 10 * time.Second

block/internal/submitting/submitter.go

Lines changed: 28 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -59,9 +59,10 @@ type Submitter struct {
5959
logger zerolog.Logger
6060

6161
// Lifecycle
62-
ctx context.Context
63-
cancel context.CancelFunc
64-
wg sync.WaitGroup
62+
ctx context.Context
63+
cancel context.CancelFunc
64+
wg sync.WaitGroup
65+
retriesBeforeHalt map[uint64]uint64
6566
}
6667

6768
// NewSubmitter creates a new DA submitter component
@@ -78,17 +79,18 @@ func NewSubmitter(
7879
errorCh chan<- error,
7980
) *Submitter {
8081
return &Submitter{
81-
store: store,
82-
exec: exec,
83-
cache: cache,
84-
metrics: metrics,
85-
config: config,
86-
genesis: genesis,
87-
daSubmitter: daSubmitter,
88-
signer: signer,
89-
daStateMtx: &sync.RWMutex{},
90-
errorCh: errorCh,
91-
logger: logger.With().Str("component", "submitter").Logger(),
82+
store: store,
83+
exec: exec,
84+
cache: cache,
85+
metrics: metrics,
86+
config: config,
87+
genesis: genesis,
88+
daSubmitter: daSubmitter,
89+
signer: signer,
90+
daStateMtx: &sync.RWMutex{},
91+
errorCh: errorCh,
92+
logger: logger.With().Str("component", "submitter").Logger(),
93+
retriesBeforeHalt: make(map[uint64]uint64),
9294
}
9395
}
9496

@@ -217,12 +219,21 @@ func (s *Submitter) processDAInclusionLoop() {
217219
break
218220
}
219221

222+
retry:
220223
// Set final height in executor
221224
if err := s.exec.SetFinal(s.ctx, nextHeight); err != nil {
222-
s.sendCriticalError(fmt.Errorf("failed to set final height: %w", err))
223-
s.logger.Error().Err(err).Uint64("height", nextHeight).Msg("failed to set final height")
224-
break
225+
s.retriesBeforeHalt[header.Height()]++
226+
if s.retriesBeforeHalt[header.Height()] > common.MaxRetriesBeforeHalt {
227+
s.sendCriticalError(fmt.Errorf("failed to set final height: %w", err))
228+
s.logger.Error().Err(err).Uint64("height", nextHeight).Msg("failed to set final height")
229+
return
230+
}
231+
232+
time.Sleep(common.MaxRetriesTimeout) // sleep before retrying
233+
s.logger.Error().Err(err).Msgf("failed to set final height (retry %d / %d): %w", s.retriesBeforeHalt[header.Height()], common.MaxRetriesBeforeHalt, err)
234+
goto retry
225235
}
236+
delete(s.retriesBeforeHalt, header.Height())
226237

227238
// Update DA included height
228239
s.SetDAIncludedHeight(nextHeight)

block/internal/syncing/syncer.go

Lines changed: 3 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -30,13 +30,6 @@ type p2pHandler interface {
3030
ProcessDataRange(ctx context.Context, fromHeight, toHeight uint64) []common.DAHeightEvent
3131
}
3232

33-
const (
34-
// maxRetriesBeforeHalt is the maximum number of retries against the execution client before halting the syncer.
35-
maxRetriesBeforeHalt = 3
36-
// maxRetriesTimeout is the maximum time to wait for a retry before halting the syncer.
37-
maxRetriesTimeout = time.Second * 10
38-
)
39-
4033
// Syncer handles block synchronization from DA and P2P sources.
4134
type Syncer struct {
4235
// Core components
@@ -493,13 +486,13 @@ func (s *Syncer) applyBlock(header types.Header, data *types.Data, currentState
493486
header.Time(), currentState.AppHash)
494487
if err != nil {
495488
s.retriesBeforeHalt[header.Height()]++
496-
if s.retriesBeforeHalt[header.Height()] > maxRetriesBeforeHalt {
489+
if s.retriesBeforeHalt[header.Height()] > common.MaxRetriesBeforeHalt {
497490
s.sendCriticalError(fmt.Errorf("failed to execute transactions: %w", err))
498491
return types.State{}, fmt.Errorf("failed to execute transactions: %w", err)
499492
}
500493

501-
time.Sleep(maxRetriesTimeout) // sleep before retrying
502-
return types.State{}, fmt.Errorf("failed to execute transactions (retry %d / %d): %w", s.retriesBeforeHalt[header.Height()], maxRetriesBeforeHalt, err)
494+
time.Sleep(common.MaxRetriesTimeout) // sleep before retrying
495+
return types.State{}, fmt.Errorf("failed to execute transactions (retry %d / %d): %w", s.retriesBeforeHalt[header.Height()], common.MaxRetriesBeforeHalt, err)
503496
}
504497
delete(s.retriesBeforeHalt, header.Height())
505498

0 commit comments

Comments
 (0)