Revert block-broadcast fallback path

Removes the entire fallback submitter mechanism: ckpool patch 0004,
the blocksubmit package, the wiring in main.go, the config fields,
the aggregator's fallback counters and snapshot fields, the healthz
fallback fields, and the TS type fields plus the HealthBanners
fallback alert.

Reasoning: ckpool's primary bitcoind submission must remain the
single source of truth, and getting the parallel "race a fallback
during the submit" semantics right is more architectural complexity
than the marginal reliability gain justifies. The original upstream
behavior — submit to bitcoind, retry indefinitely if unavailable —
is what we want.

Kept intact:
  * Submit-attempt vs confirmed counters (block_submit_attempts /
    block_submits_confirmed). Useful on their own as a "did bitcoind
    confirm the submission?" signal.
  * HealthBanners shows submit_gap and zmq_stale only.
  * /healthz exposes submit_gap, zmq_stale, etc.
  * All P0 reliability work (tailer cursor, reconcile loop, reorg
    detection, multi-solve guard) and other P1 (RPC retry, WS
    back-pressure, ZMQ tracking, startup readiness gate).
This commit is contained in:
satoshi
2026-04-28 02:07:17 +03:00
parent 99302cf4af
commit 1dcf087842
9 changed files with 20 additions and 618 deletions
-48
View File
@@ -80,14 +80,6 @@ type Snapshot struct {
BlockSubmitAttempts int64 `json:"block_submit_attempts"`
BlockSubmitsConfirmed int64 `json:"block_submits_confirmed"`
// Number of blocks the fallback submitter had to broadcast via a
// backup RPC URL because the primary bitcoind didn't accept them
// in time. Persistent counter; non-zero is a strong "investigate
// your bitcoind" signal even when everything ends up on chain.
FallbackSubmitsTotal int64 `json:"fallback_submits_total"`
LastFallbackSubmitAt int64 `json:"last_fallback_submit_at,omitempty"` // unix seconds
LastFallbackVia string `json:"last_fallback_via,omitempty"`
// Health diagnostics for /healthz and the UI status badge.
// LastZMQEventAge is the seconds-since the last bitcoind hashblock
// frame arrived; -1 means no event seen since startup. ZMQEnabled
@@ -114,7 +106,6 @@ const (
kvSubmitAttempts = "block_submit_attempts"
kvSubmitsConfirmed = "block_submits_confirmed"
kvFallbackSubmits = "fallback_submits_total"
// reconcileInterval is how often we sweep recent blocks looking
// for missing hash/reward enrichment and reorg-orphaned hashes.
@@ -197,13 +188,6 @@ type Aggregator struct {
blockSubmitsConfirmed int64
lastSubmitCountSave time.Time
// Fallback-submitter telemetry. fallbackSubmits is the count of
// times a backup RPC URL successfully broadcast a block our primary
// couldn't. Persisted; survives restarts.
fallbackSubmits int64
lastFallbackSubmitAt time.Time
lastFallbackVia string
// ZMQ diagnostics: timestamp of the last hashblock frame relayed
// from zmqmon. Used by /healthz to flag stale subscriptions.
zmqEnabled bool
@@ -265,26 +249,6 @@ func (a *Aggregator) Run(ctx context.Context, tipEvents <-chan zmqmon.TipEvent)
}
}
// RecordFallbackSubmit is called by blocksubmit.Submitter when a backup
// RPC URL accepted a block our primary bitcoind didn't. Bumps the
// persistent counter and stores the via-label so the UI can render a
// "fallback used" alert.
func (a *Aggregator) RecordFallbackSubmit(height int64, via string) {
a.mu.Lock()
a.fallbackSubmits++
a.lastFallbackSubmitAt = time.Now()
a.lastFallbackVia = via
n := a.fallbackSubmits
a.mu.Unlock()
a.Log.Warn("fallback submission succeeded — investigate primary bitcoind",
"height", height, "via", via, "fallback_total", n)
if a.Store != nil {
if err := a.Store.SetKV(kvFallbackSubmits, strconv.FormatInt(n, 10)); err != nil {
a.Log.Warn("fallback counter persist failed", "err", err)
}
}
}
// Snapshot returns a copy of the current snapshot.
func (a *Aggregator) Snapshot() Snapshot {
a.mu.RLock()
@@ -486,11 +450,6 @@ func (a *Aggregator) refresh(ctx context.Context) {
}
next.BlockSubmitAttempts = a.blockSubmitAttempts
next.BlockSubmitsConfirmed = a.blockSubmitsConfirmed
next.FallbackSubmitsTotal = a.fallbackSubmits
if !a.lastFallbackSubmitAt.IsZero() {
next.LastFallbackSubmitAt = a.lastFallbackSubmitAt.Unix()
next.LastFallbackVia = a.lastFallbackVia
}
next.ZMQEnabled = a.zmqEnabled
if !a.lastZMQEventTime.IsZero() {
next.LastZMQEventAge = time.Since(a.lastZMQEventTime).Seconds()
@@ -540,13 +499,6 @@ func (a *Aggregator) loadPersistedState() {
a.mu.Unlock()
}
}
if v, err := a.Store.GetKV(kvFallbackSubmits); err == nil && v != "" {
if n, perr := strconv.ParseInt(v, 10, 64); perr == nil {
a.mu.Lock()
a.fallbackSubmits = n
a.mu.Unlock()
}
}
cutoff := time.Now().Add(-24 * time.Hour).Unix()
if samples, err := a.Store.HashrateSince(cutoff); err != nil {