Skip to content

test(sdk): add proof-vector regression corpus for drive-proof-verifier - #4345

Merged
QuantumExplorer merged 1 commit into
v4.2-devfrom
feat/drive-proof-verifier-corpus
Aug 9, 2026
Merged

test(sdk): add proof-vector regression corpus for drive-proof-verifier#4345
QuantumExplorer merged 1 commit into
v4.2-devfrom
feat/drive-proof-verifier-corpus

Conversation

@PastaPastaPasta

@PastaPastaPasta PastaPastaPasta commented Aug 8, 2026

Copy link
Copy Markdown
Member

Issue being fixed or feature implemented

drive-proof-verifier is the trust boundary for every Platform client that verifies proofs — yet it has no integration tests: its pipeline (grovedb proof replay + tenderdash quorum-signature check) is exercised only indirectly through rs-sdk's mock replay. Nothing in the repo pins that a proof generated by a real Drive state verifies through the crate's public entry points, or that tampering any single ingredient breaks verification at the intended layer.

Second standalone slice of #4335 (after #4344); independent of both — test-only, no API changes, Cargo.lock untouched apart from dev-deps.

What was done?

A corpus of 16 fixture directories generated from a real Drive state (platform v4.0.0 fixtures, protocol version 12), driving 19 test cases through the crate's real public FromProof entry points. Each case is a self-contained directory: manifest.json (request params, block metadata, expected outcome, pinned root hash) + proof.hex / signature.hex / quorum_pubkey.hex. A loader synthesizes the DAPI response protobuf from components; a VectorContextProvider serves the per-case quorum key and errors on any unknown quorum, so a loader bug cannot vacuously pass.

Designed for the "is this test actually testing something" question:

  • Positives assert decoded values, not is_ok(): balances, nonces, key bytes and ordering, contender tallies, winner identities, and Ok(None) proof-of-absence — all against the manifest.
  • Every quorum-sig positive runs a genuine BLS check: all drive fixtures commit to one root hash, which is exactly the app hash the fixture quorum signature signs, with real 48-byte key material.
  • Negatives change exactly one ingredient each, so none can pass for the wrong reason: bit-flipped proof → fails at the grovedb layer (signature bytes untouched); tampered signature → point decompression failure; wrong quorum key (same quorum hash, different key bytes) and wrong block-id hash → signature verification failure; and tampering any signed ResponseMetadata field (height, time_ms, core_chain_locked_height) breaks the signature — pinning that the StateId digest genuinely covers the metadata a client acts on. Never a panic.
  • The documents-family cases are labeled for exactly what they reach: they pin the DriveDocumentQuery shape (root hash + serialized payloads byte-for-byte) and clean decode failure on the fixture's placeholder payloads; the coverage matrix in tests/vectors/README.md states per-family what is and isn't exercised, including that these four stop before the signature layer. A real-document fixture for one true end-to-end documents positive is called out as regeneration follow-up.

The same fixtures are replayed byte-exact by Dash Core's platform GUI implementation (PastaPastaPasta/dash#67), so this corpus doubles as a cross-implementation anchor: drift between what Drive proves and what any client verifies fails loudly here.

Suite is gated behind the existing mocks feature: cargo test -p drive-proof-verifier --features mocks.

How Has This Been Tested?

  • cargo test -p drive-proof-verifier --features mocks: 261 existing lib tests + 19 new vector tests + doctests, all passing on current v4.2-dev.
  • cargo fmt --check and cargo clippy -p drive-proof-verifier --all-features --all-targets -- -D warnings clean.
  • Corpus size: ~260 KB total, hand-trimmed, no LFS.

Breaking Changes

None. Test-only; dev-dependency additions to rs-drive-proof-verifier only.

Checklist:

  • I have performed a self-review of my own code
  • I have commented my code, particularly in hard-to-understand areas
  • I have added or updated relevant unit/integration/functional/e2e tests
  • I have made corresponding changes to the documentation
  • I have assigned this pull request to a milestone (for repository code-owners and collaborators only)

🤖 Generated with Claude Code

Summary by CodeRabbit

  • Tests

    • Added regression coverage for identity balances, nonces, contract nonces, public keys, DPNS queries, DashPay documents, and contested vote states.
    • Added validation for valid and corrupted proofs, including tampered signatures, quorum keys, block hashes, and response metadata.
    • Added reusable proof-vector fixtures and test infrastructure for reproducing verification scenarios.
  • Documentation

    • Documented the proof-vector corpus, coverage, provenance, and regeneration process.

@thepastaclaw

thepastaclaw commented Aug 8, 2026

Copy link
Copy Markdown
Collaborator

🔍 Review in progress — actively reviewing now (commit 968d12b)

@coderabbitai

coderabbitai Bot commented Aug 8, 2026

Copy link
Copy Markdown
Contributor

Review Change Stack

Warning

Review limit reached

@PastaPastaPasta, you've reached your PR review limit, so we couldn't start this review.

Next review available in: 1 minute

Enable usage-based reviews in Billing to review now. Otherwise, wait until the next included review is available.
You're only billed for reviews past your plan's rate limits ($0.25/file).

How can I continue?

After more reviews become available, a review can be triggered using the @coderabbitai review command as a PR comment. Alternatively, push new commits to this PR.

To avoid repeated limits, reduce automatic review volume by pausing incremental auto-reviews earlier, using label-based review opt-in, excluding WIP or generated PR titles, or requesting reviews manually when the PR is ready. If your team needs uninterrupted high-volume reviews, an organization admin can enable usage-based reviews.

How do review limits work?

CodeRabbit enforces per-developer PR review limits for each organization. Most developers receive the normal plan review availability.

For paid Pro and Pro+ PR reviews, CodeRabbit uses adaptive limits for sustained high-volume activity. When a developer's recent PR review activity reaches the 95th percentile or higher among CodeRabbit users, additional reviews become available more gradually as earlier reviews age out of the rolling window.

Please refer docs for additional details.

Review details
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro Plus

Run ID: 896d7c01-09ef-4736-983d-b7a59a3646c1

📥 Commits

Reviewing files that changed from the base of the PR and between b7acc65 and 968d12b.

⛔ Files ignored due to path filters (1)
  • Cargo.lock is excluded by !**/*.lock
📒 Files selected for processing (1)
  • packages/rs-drive-proof-verifier/tests/vectors_identity.rs
📝 Walkthrough

Walkthrough

Added shared proof-vector loading infrastructure and mock-gated regression tests for identity, quorum signatures, documents, and contested vote states.

Changes

Proof verifier regression corpus

Layer / File(s) Summary
Corpus loader and verification context
packages/rs-drive-proof-verifier/Cargo.toml, packages/rs-drive-proof-verifier/tests/common/mod.rs, packages/rs-drive-proof-verifier/tests/vectors/README.md
Added fixture dependencies, manifest models, corpus loading, gRPC metadata construction, and the vector context provider.
Identity and quorum-signature vectors
packages/rs-drive-proof-verifier/tests/vectors_identity.rs, packages/rs-drive-proof-verifier/tests/vectors_quorum_sig.rs, packages/rs-drive-proof-verifier/tests/vectors/identity-*/, packages/rs-drive-proof-verifier/tests/vectors/quorum-sig-*/
Added identity balance, nonce, contract nonce, key, corrupted-proof, and quorum-signature regression cases.
Document proof vectors
packages/rs-drive-proof-verifier/tests/vectors_documents.rs, packages/rs-drive-proof-verifier/tests/vectors/dpns-*/, packages/rs-drive-proof-verifier/tests/vectors/dashpay-*/
Added DPNS and DashPay query vectors, root-hash checks, serialized payload checks, and document decoding-error assertions.
Contested vote-state vectors
packages/rs-drive-proof-verifier/tests/vectors_contested.rs, packages/rs-drive-proof-verifier/tests/vectors/contested-vote-state-*/
Added active, finished, and absent contest cases with contender, tally, winner, finalization, and absence assertions.

Estimated code review effort: 3 (Moderate) | ~30 minutes

Possibly related PRs

  • dashpay/platform#4281: Shares contested-vote proof behavior, but changes document-creation validation instead of verifier regression tests.

Suggested reviewers: lklimek, shumkov, quantumexplorer

🚥 Pre-merge checks | ✅ 5
✅ Passed checks (5 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title clearly and concisely describes the added proof-vector regression corpus for drive-proof-verifier.
Docstring Coverage ✅ Passed Docstring coverage is 84.85% which is sufficient. The required threshold is 80.00%.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.
✨ Finishing Touches 💡 1
🛠️ Fix failing CI checks 💡
  • Create stacked PR
  • Commit on current branch
📝 Generate docstrings
  • Create stacked PR
  • Commit on current branch
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch feat/drive-proof-verifier-corpus

Comment @coderabbitai help to get the list of available commands.

@codecov

codecov Bot commented Aug 8, 2026

Copy link
Copy Markdown

Codecov Report

✅ All modified and coverable lines are covered by tests.
✅ Project coverage is 87.62%. Comparing base (7a7ec9f) to head (968d12b).
⚠️ Report is 1 commits behind head on v4.2-dev.

Additional details and impacted files
@@            Coverage Diff            @@
##           v4.2-dev    #4345   +/-   ##
=========================================
  Coverage     87.62%   87.62%           
=========================================
  Files          2704     2704           
  Lines        345206   345206           
=========================================
+ Hits         302473   302474    +1     
+ Misses        42733    42732    -1     
Components Coverage Δ
dpp 88.86% <ø> (ø)
drive 86.25% <ø> (ø)
drive-abci 89.66% <ø> (+<0.01%) ⬆️
sdk ∅ <ø> (∅)
dapi-client ∅ <ø> (∅)
platform-version ∅ <ø> (∅)
platform-value 92.88% <ø> (ø)
platform-wallet ∅ <ø> (∅)
drive-proof-verifier 48.02% <ø> (ø)
🚀 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.

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Actionable comments posted: 1

🧹 Nitpick comments (1)
packages/rs-drive-proof-verifier/tests/vectors_contested.rs (1)

161-164: 🎯 Functional Correctness | 🔵 Trivial | 🏗️ Heavy lift

Assert the expected finalization block data.

This assertion accepts any nonzero time_ms. A wrong finalization timestamp, height, epoch, or chain-lock height can pass the regression test. Add expected finalization metadata to the finished manifest and assert the complete returned block data.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@packages/rs-drive-proof-verifier/tests/vectors_contested.rs` around lines 161
- 164, Update the finished manifest and the assertion near finalization_block to
define expected finalization metadata, then assert the complete returned block
data rather than only checking finalization_block.time_ms > 0. Verify the
expected timestamp, height, epoch, and chain-lock height against the returned
finalization block while preserving the existing presence validation.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@packages/rs-drive-proof-verifier/tests/vectors_identity.rs`:
- Around line 156-164: Run cargo fmt on
packages/rs-drive-proof-verifier/tests/vectors_identity.rs, ensuring the result
field in the GetIdentityContractNonceResponse construction is wrapped
consistently with the equivalent proof responses in that file.

---

Nitpick comments:
In `@packages/rs-drive-proof-verifier/tests/vectors_contested.rs`:
- Around line 161-164: Update the finished manifest and the assertion near
finalization_block to define expected finalization metadata, then assert the
complete returned block data rather than only checking
finalization_block.time_ms > 0. Verify the expected timestamp, height, epoch,
and chain-lock height against the returned finalization block while preserving
the existing presence validation.
🪄 Autofix

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro Plus

Run ID: 807e12f2-00fe-4089-b46b-682d545fb796

📥 Commits

Reviewing files that changed from the base of the PR and between 7a7ec9f and b7acc65.

📒 Files selected for processing (71)
  • packages/rs-drive-proof-verifier/Cargo.toml
  • packages/rs-drive-proof-verifier/tests/common/mod.rs
  • packages/rs-drive-proof-verifier/tests/vectors/README.md
  • packages/rs-drive-proof-verifier/tests/vectors/contested-vote-state-absent/manifest.json
  • packages/rs-drive-proof-verifier/tests/vectors/contested-vote-state-absent/proof.hex
  • packages/rs-drive-proof-verifier/tests/vectors/contested-vote-state-absent/quorum_pubkey.hex
  • packages/rs-drive-proof-verifier/tests/vectors/contested-vote-state-absent/signature.hex
  • packages/rs-drive-proof-verifier/tests/vectors/contested-vote-state-active/manifest.json
  • packages/rs-drive-proof-verifier/tests/vectors/contested-vote-state-active/proof.hex
  • packages/rs-drive-proof-verifier/tests/vectors/contested-vote-state-active/quorum_pubkey.hex
  • packages/rs-drive-proof-verifier/tests/vectors/contested-vote-state-active/signature.hex
  • packages/rs-drive-proof-verifier/tests/vectors/contested-vote-state-finished/manifest.json
  • packages/rs-drive-proof-verifier/tests/vectors/contested-vote-state-finished/proof.hex
  • packages/rs-drive-proof-verifier/tests/vectors/contested-vote-state-finished/quorum_pubkey.hex
  • packages/rs-drive-proof-verifier/tests/vectors/contested-vote-state-finished/signature.hex
  • packages/rs-drive-proof-verifier/tests/vectors/dashpay-contacts-incoming/manifest.json
  • packages/rs-drive-proof-verifier/tests/vectors/dashpay-contacts-incoming/proof.hex
  • packages/rs-drive-proof-verifier/tests/vectors/dashpay-contacts-incoming/quorum_pubkey.hex
  • packages/rs-drive-proof-verifier/tests/vectors/dashpay-contacts-incoming/signature.hex
  • packages/rs-drive-proof-verifier/tests/vectors/dashpay-profile/manifest.json
  • packages/rs-drive-proof-verifier/tests/vectors/dashpay-profile/proof.hex
  • packages/rs-drive-proof-verifier/tests/vectors/dashpay-profile/quorum_pubkey.hex
  • packages/rs-drive-proof-verifier/tests/vectors/dashpay-profile/signature.hex
  • packages/rs-drive-proof-verifier/tests/vectors/dpns-domain-exact/manifest.json
  • packages/rs-drive-proof-verifier/tests/vectors/dpns-domain-exact/proof.hex
  • packages/rs-drive-proof-verifier/tests/vectors/dpns-domain-exact/quorum_pubkey.hex
  • packages/rs-drive-proof-verifier/tests/vectors/dpns-domain-exact/signature.hex
  • packages/rs-drive-proof-verifier/tests/vectors/dpns-domain-prefix/manifest.json
  • packages/rs-drive-proof-verifier/tests/vectors/dpns-domain-prefix/proof.hex
  • packages/rs-drive-proof-verifier/tests/vectors/dpns-domain-prefix/quorum_pubkey.hex
  • packages/rs-drive-proof-verifier/tests/vectors/dpns-domain-prefix/signature.hex
  • packages/rs-drive-proof-verifier/tests/vectors/identity-balance-corrupted-proof/manifest.json
  • packages/rs-drive-proof-verifier/tests/vectors/identity-balance-corrupted-proof/proof.hex
  • packages/rs-drive-proof-verifier/tests/vectors/identity-balance-corrupted-proof/quorum_pubkey.hex
  • packages/rs-drive-proof-verifier/tests/vectors/identity-balance-corrupted-proof/signature.hex
  • packages/rs-drive-proof-verifier/tests/vectors/identity-balance/manifest.json
  • packages/rs-drive-proof-verifier/tests/vectors/identity-balance/proof.hex
  • packages/rs-drive-proof-verifier/tests/vectors/identity-balance/quorum_pubkey.hex
  • packages/rs-drive-proof-verifier/tests/vectors/identity-balance/signature.hex
  • packages/rs-drive-proof-verifier/tests/vectors/identity-contract-nonce/manifest.json
  • packages/rs-drive-proof-verifier/tests/vectors/identity-contract-nonce/proof.hex
  • packages/rs-drive-proof-verifier/tests/vectors/identity-contract-nonce/quorum_pubkey.hex
  • packages/rs-drive-proof-verifier/tests/vectors/identity-contract-nonce/signature.hex
  • packages/rs-drive-proof-verifier/tests/vectors/identity-keys/manifest.json
  • packages/rs-drive-proof-verifier/tests/vectors/identity-keys/proof.hex
  • packages/rs-drive-proof-verifier/tests/vectors/identity-keys/quorum_pubkey.hex
  • packages/rs-drive-proof-verifier/tests/vectors/identity-keys/signature.hex
  • packages/rs-drive-proof-verifier/tests/vectors/identity-nonce/manifest.json
  • packages/rs-drive-proof-verifier/tests/vectors/identity-nonce/proof.hex
  • packages/rs-drive-proof-verifier/tests/vectors/identity-nonce/quorum_pubkey.hex
  • packages/rs-drive-proof-verifier/tests/vectors/identity-nonce/signature.hex
  • packages/rs-drive-proof-verifier/tests/vectors/quorum-sig-tampered-signature/manifest.json
  • packages/rs-drive-proof-verifier/tests/vectors/quorum-sig-tampered-signature/proof.hex
  • packages/rs-drive-proof-verifier/tests/vectors/quorum-sig-tampered-signature/quorum_pubkey.hex
  • packages/rs-drive-proof-verifier/tests/vectors/quorum-sig-tampered-signature/signature.hex
  • packages/rs-drive-proof-verifier/tests/vectors/quorum-sig-valid/manifest.json
  • packages/rs-drive-proof-verifier/tests/vectors/quorum-sig-valid/proof.hex
  • packages/rs-drive-proof-verifier/tests/vectors/quorum-sig-valid/quorum_pubkey.hex
  • packages/rs-drive-proof-verifier/tests/vectors/quorum-sig-valid/signature.hex
  • packages/rs-drive-proof-verifier/tests/vectors/quorum-sig-wrong-block-id-hash/manifest.json
  • packages/rs-drive-proof-verifier/tests/vectors/quorum-sig-wrong-block-id-hash/proof.hex
  • packages/rs-drive-proof-verifier/tests/vectors/quorum-sig-wrong-block-id-hash/quorum_pubkey.hex
  • packages/rs-drive-proof-verifier/tests/vectors/quorum-sig-wrong-block-id-hash/signature.hex
  • packages/rs-drive-proof-verifier/tests/vectors/quorum-sig-wrong-quorum-key/manifest.json
  • packages/rs-drive-proof-verifier/tests/vectors/quorum-sig-wrong-quorum-key/proof.hex
  • packages/rs-drive-proof-verifier/tests/vectors/quorum-sig-wrong-quorum-key/quorum_pubkey.hex
  • packages/rs-drive-proof-verifier/tests/vectors/quorum-sig-wrong-quorum-key/signature.hex
  • packages/rs-drive-proof-verifier/tests/vectors_contested.rs
  • packages/rs-drive-proof-verifier/tests/vectors_documents.rs
  • packages/rs-drive-proof-verifier/tests/vectors_identity.rs
  • packages/rs-drive-proof-verifier/tests/vectors_quorum_sig.rs

Comment thread packages/rs-drive-proof-verifier/tests/vectors_identity.rs
@PastaPastaPasta
PastaPastaPasta force-pushed the feat/drive-proof-verifier-corpus branch from b7acc65 to 2028d5e Compare August 8, 2026 17:31
drive-proof-verifier had no integration tests: its verification pipeline
(grovedb proof replay + tenderdash quorum-signature check) was exercised
only indirectly through rs-sdk's mock replay. Add a corpus of 16 fixture
directories generated from a real Drive state (platform v4.0.0 fixtures,
protocol version 12) driving 19 test cases through the crate's real public
FromProof entry points, with a per-case manifest.json plus
proof/signature/quorum-key blobs and a loader that synthesizes the DAPI
response protobuf from components.

Positive cases assert decoded values against the manifest (balances,
nonces, key bytes and ordering, contender tallies, winners, proof-of-
absence), and every quorum-sig positive runs a genuine BLS check with real
fixture key material: all drive fixtures commit to one root hash, which is
exactly the app hash the fixture quorum signature signs. Negative cases
each change exactly one ingredient so none can pass for the wrong reason:
a bit-flipped proof fails at the grovedb layer, a tampered signature at
point decompression, a wrong quorum key and a wrong block-id hash at
signature verification, and tampering any signed ResponseMetadata field
(height, time_ms, core_chain_locked_height) breaks the signature - pinning
that the StateId digest really covers the metadata. Never a panic.

The documents-family cases pin the DriveDocumentQuery shape (root hash and
serialized payloads byte-for-byte) and clean decode failure on the
fixture's placeholder payloads; the coverage matrix in tests/vectors/
README.md states exactly what each family reaches. The same fixtures are
replayed byte-exact by Dash Core's platform GUI implementation, so drift
between what Drive proves and what any client verifies fails loudly here.
@PastaPastaPasta
PastaPastaPasta force-pushed the feat/drive-proof-verifier-corpus branch from 2028d5e to 968d12b Compare August 8, 2026 18:10
@QuantumExplorer
QuantumExplorer merged commit 838ae66 into v4.2-dev Aug 9, 2026
21 checks passed
@QuantumExplorer
QuantumExplorer deleted the feat/drive-proof-verifier-corpus branch August 9, 2026 07:06
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.

3 participants