Skip to content

fix(seidb-bench): stop the state-store bench backends fail on a nil config - #3838

Open
blindchaser wants to merge 1 commit into
mainfrom
fix/seidb-bench-nil-ss-config
Open

fix(seidb-bench): stop the state-store bench backends fail on a nil config#3838
blindchaser wants to merge 1 commit into
mainfrom
fix/seidb-bench-nil-ss-config

Conversation

@blindchaser

Copy link
Copy Markdown
Contributor

Summary

runBenchmark hands NewDBImpl a nil dbConfig for every backend, but the SSComposite, SSHistoricalOffload and CompositeDual_SSComposite cases still asserted dbConfig.(*T) in single-value form. That panics on a nil interface, so BenchmarkSSCompositeWrite, BenchmarkSSHistoricalOffloadWrite and BenchmarkCombinedCompositeDualSSCompositeWrite crashed at startup with interface conversion: interface {} is nil, not *config.StateStoreConfig — the same failure #3770 fixed for FlatKV, in the same switch.

Copying that fix case-by-case wouldn't be enough: with only a comma-ok assertion the crash moves one frame later, since both SS Composite constructors dereference *ssConfig. And this is now the third instance of the same bare-assertion bug in this switch, so the fix collapses config extraction into one place rather than patching instance three.

  • wrappers/db_implementations.go: backendConfig[T] becomes the single path from the untyped dbConfig to a backend's typed config. It treats nil as ordinary — each constructor supplies its own default — and rejects only a wrong type, now naming the type it wanted. All five config-taking cases route through it, so a new backend can't reintroduce the bare assertion. newSSCompositeStateStore and newCombinedCompositeDualSSComposite fall back to DefaultBenchStateStoreConfig(), matching the fallback the MemIAVL and FlatKV constructors already have. SSHistoricalOffload deliberately keeps no default: its stream needs brokers only the caller knows, so nil reaches HistoricalOffloadConfig.Validate, which already reports historical offload config is required.

Benchmark-only change; no production code path touched.

Test plan

  • go test ./sei-db/state_db/bench/wrapperswrappers_test.go gains two table tests over every config-taking backend: nil resolves to the default and opens, a wrong type errors with the backend named. Plus an offload-specific case asserting the missing config is reported rather than panicked. The two FlatKV-only tests from fix(seidb-bench): tolerate nil FlatKV config in bench wrapper factory #3770 are folded into those tables.
  • Before, on main: BenchmarkSSCompositeWritepanic: interface conversion: interface {} is nil, not *config.StateStoreConfig
  • After, both benchmarks run to completion:
    BenchmarkSSCompositeWrite/100_keys_per_block-11 1 32137667 ns/op 311161 keys/sec
    BenchmarkCombinedCompositeDualSSCompositeWrite/100_keys_per_block-11 1 174587333 ns/op 57278 keys/sec
  • After, BenchmarkSSHistoricalOffloadWrite fails with failed to create historical offload stream: historical offload config is required instead of panicking (it needs a live Kafka broker to actually run)
  • go vet / gofmt -s / goimports clean

…nil config

runBenchmark hands NewDBImpl a nil dbConfig for every backend, but the
SSComposite, SSHistoricalOffload and CompositeDual_SSComposite cases still
asserted dbConfig.(*T) without the comma-ok form. A single-value assertion on
a nil interface panics, so BenchmarkSSCompositeWrite,
BenchmarkSSHistoricalOffloadWrite and BenchmarkCombinedCompositeDualSSComposite
crashed at startup — the same failure #3770 fixed for FlatKV, in the same
switch. Merely copying that fix would only move the crash one frame later,
since both SS Composite constructors dereference the config.

Route every case through one generic helper that treats nil as ordinary and
only rejects a wrong type, and let the two SS Composite constructors fall back
to DefaultBenchStateStoreConfig the way the MemIAVL and FlatKV ones already
fall back to theirs. SSHistoricalOffload keeps no default: its stream needs
brokers only the caller knows, so it now reports "historical offload config is
required" instead of crashing.

The first two benchmarks run to completion again; the offload one fails with
that message.

Co-authored-by: Cursor <cursoragent@cursor.com>
@cursor

cursor Bot commented Aug 1, 2026

Copy link
Copy Markdown

PR Summary

Low Risk
Changes are confined to sei-db benchmark wrappers and tests; production DB paths are untouched.

Overview
Fixes benchmark startup panics when runBenchmark passes a nil dbConfig into NewDBImpl for state-store backends (SSComposite, CompositeDual_SSComposite, and related cases that used bare dbConfig.(*T) assertions).

Introduces generic backendConfig[T] so nil config is passed through (constructors apply defaults) and only wrong types return a named error. newSSCompositeStateStore and newCombinedCompositeDualSSComposite now use DefaultBenchStateStoreConfig() when config is nil, matching MemIAVL/FlatKV. SSHistoricalOffload still has no default; nil config surfaces historical offload config is required from validation instead of panicking.

Tests are broadened to table-driven coverage: nil opens for backends with defaults, invalid types error per backend, and offload nil is an error not a panic.

Reviewed by Cursor Bugbot for commit f9b74de. Bugbot is set up for automated code reviews on this repo. Configure here.

@github-actions

github-actions Bot commented Aug 1, 2026

Copy link
Copy Markdown

The latest Buf updates on your PR. Results from workflow Buf / buf (pull_request).

BuildFormatLintBreakingUpdated (UTC)
✅ passed✅ passed✅ passed✅ passedAug 1, 2026, 2:28 AM

@seidroid seidroid Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Benchmark-only fix that correctly collapses three panicking bare type assertions in NewDBImpl into one generic backendConfig[T] helper, with nil-config defaults added to the two SS Composite constructors and table tests covering all five config-taking backends. I found no correctness or security issues; only a minor test-coverage gap and one consistency nit.

Findings: 0 blocking | 4 non-blocking | 1 posted inline

Blockers

  • None at the file/PR level.

Non-blocking

  • cursor-review.md is empty — the Cursor pass produced no output, so this review reflects only the Claude and Codex passes (Codex reported no material issues).
  • The non-config backends (NoOp, CompositeDual, CompositeSplit, CompositeCosmos) still silently discard a non-nil dbConfig. Now that config extraction is centralized in backendConfig, it would be cheap and consistent to reject a supplied config for those cases too, so a misrouted config surfaces as an error instead of being ignored. Non-blocking, pre-existing behavior.
  • Pre-existing, worth noting since backendConfig now returns the caller's pointer verbatim: newFlatKVCommitStore mutates the caller's config (config.DataDir = dbDir) and HistoricalOffloadConfig.Validate mutates the caller's Kafka sub-config via applyDefaults. Harmless for bench single-open usage, but a copy-on-entry would make the helper's contract fully read-only.
  • 1 suggestion(s)/nit(s) flagged inline on specific lines.

require.ErrorContains(t, err, "historical offload config is required")
}

func TestNewDBImplRejectsInvalidConfigType(t *testing.T) {

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

[suggestion] The two tables cover the nil path and the wrong-type path, but nothing asserts the third branch of backendConfig — that a correctly-typed non-nil config is passed through and actually honored rather than silently replaced by the backend default. A small case (e.g. open SSComposite with a *config.StateStoreConfig whose EVMSplit/AsyncWriteBuffer differs from DefaultBenchStateStoreConfig(), and assert the store reflects it) would lock in the behavior cryptosim.go:146 depends on when the user supplies a config.

@claude claude Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM — benchmark-only fix, well-tested.

Extended reasoning...

Overview

Two-file change confined to sei-db/state_db/bench/wrappers: a benchmark harness that instantiates DB backends for micro-benchmarking. The PR generalizes the fix from #3770 (nil-config panic on FlatKV) into a single backendConfig[T] generic helper used by all five config-taking cases in NewDBImpl's switch, replacing bare dbConfig.(*T) type assertions that panic on nil interfaces.

Security risks

None. This code only runs under go test/go bench in the benchmark package; it is never invoked from any production binary or RPC path, and touches no auth, crypto, or user-facing input.

Level of scrutiny

Low. Non-production, test/benchmark-only code with a narrow, mechanical fix pattern (replace panic-prone assertions with a helper that treats nil as valid and wrong-type as an error). I verified the one subtlety called out in the description — HistoricalOffloadConfig.Validate() has a nil receiver check (if c == nil { return fmt.Errorf("historical offload config is required") }) — matches the code in historical_offload_wrapper.go, so the claimed non-panic behavior for that backend is correct.

Other factors

Test coverage is thorough: table-driven tests cover nil-config defaulting for every backend that has a default, wrong-type rejection for every backend, and the one backend (SSHistoricalOffload) that intentionally has no default. The diff is small, self-contained, and matches an established prior-fix pattern (#3770) rather than introducing new design decisions.

@codecov

codecov Bot commented Aug 1, 2026

Copy link
Copy Markdown

Codecov Report

✅ All modified and coverable lines are covered by tests.
✅ Project coverage is 60.40%. Comparing base (438cc04) to head (f9b74de).

Additional details and impacted files

Impacted file tree graph

@@            Coverage Diff             @@
##             main    #3838      +/-   ##
==========================================
- Coverage   61.29%   60.40%   -0.90%     
==========================================
  Files        2351     2259      -92     
  Lines      197491   186867   -10624     
==========================================
- Hits       121060   112879    -8181     
+ Misses      65579    63988    -1591     
+ Partials    10852    10000     -852     
Flag Coverage Δ
sei-db 70.41% <ø> (+1.04%) ⬆️
sei-db-state-db ?

Flags with carried forward coverage won't be shown. Click here to find out more.
see 97 files with indirect coverage changes

🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.
  • 📦 JS Bundle Analysis: Save yourself from yourself by tracking and limiting bundle sizes in JS merges.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant