Skip to content

issue #1535: make error discriminants append-only and fixture-checked - #1674

Merged
Jagadeeshftw merged 1 commit into
Fluxora-Org:mainfrom
ValJnr-dev1:issue-1535-error-discriminants-fixture
Aug 31, 2026
Merged

issue #1535: make error discriminants append-only and fixture-checked#1674
Jagadeeshftw merged 1 commit into
Fluxora-Org:mainfrom
ValJnr-dev1:issue-1535-error-discriminants-fixture

Conversation

@ValJnr-dev1

Copy link
Copy Markdown
Contributor

Summary

Closes #1535

Error discriminants are part of the public ABI: a client decodes an on-chain Error(Contract, #N) against a fixed table, and silently renumbering a variant breaks every integration that relied on that number without any compile-time warning.

Before

error.rs had explicit = N values for all 31 variants, but nothing in the test suite checked those values. A developer could renumber a variant and the CI suite would pass while every downstream client broke.

After

Two files changed:

contracts/stream/src/test/error_discriminants.rs (new)

  1. DISCRIMINANT_FIXTURE -- a const table mapping every variant name to its frozen u32 value (all 31 variants, 1-31). This is the canonical append registry.
  2. LAST_DISCRIMINANT = 31 -- marks the append boundary. New variants must use LAST_DISCRIMINANT + 1 and add a row to the fixture.
  3. discriminant_fixture_is_complete_and_contiguous -- asserts the fixture covers 1..=LAST_DISCRIMINANT with no gaps or misordering, catching authoring errors in the fixture itself.
  4. discriminant_fixture_matches_source -- casts every Error::Variant as u32 at runtime and compares against the fixture. Any = N change in error.rs fails this test immediately with a clear message: RENUMBERING DETECTED -- revert the change in error.rs. Only append new variants; never renumber existing ones. Prints the full discriminant table with --nocapture as required by the issue.
  5. Public error-path tests -- every error variant reachable through a try_* client call is driven to that exact error at least once (covers Implement contract storage (Config, stream map, next_stream_id) #1-feat: set stream status to Completed when fully withdrawn #23, Feat/get stream state and tests #27-feat: emit StreamCreated event on create_stream #28, feat: Stream Event Definitions #30). Variants not reachable via public try_* paths in the test host (TokenMissing Implemented recipient-only authorization for the withdraw function #26, MalformedStreamId feat: Defined a Withdrawal event (stream_id, recipient, amount) and emit it on each successful withdraw. #29, StreamIdExhausted feat: implement resume_stream with auth and Active status transition closes #10 #24, TokenTransferFailed feat: implemented withdraw #25, InvalidTopUp fix: add overflow and safety checks to calculate_accrued #31) are confirmed by discriminant-cast assertions with inline explanations.

contracts/stream/src/test/mod.rs

Registered mod error_discriminants under the ABI inventory block.

Verification

Issue verification command:

cargo test -p fluxora-stream error -- --nocapture

Output (abridged):

=== error discriminant fixture (31 variants) ===
    1  StreamNotFound
    2  InvalidTimeRange
    3  InvalidCliff
    4  InvalidDeposit
    5  DepositRateTooLow
    6  SelfStream
    7  Unauthorized
    8  NotCancellable
    9  NotPausable
   10  NotTransferable
   11  StreamNotActive
   12  StreamNotPaused
   13  StreamAlreadyPaused
   14  StreamTerminated
   15  StreamMatured
   16  InsufficientWithdrawable
   17  NothingToWithdraw
   18  InvalidAmount
   19  BatchTooLarge
   20  EmptyBatch
   21  DuplicateStreamId
   22  Overflow
   23  TopUpTooSmall
   24  StreamIdExhausted
   25  TokenTransferFailed
   26  TokenMissing
   27  DelegateNotPermitted
   28  DelegateExpired
   29  MalformedStreamId
   30  RepeatedTransfer
   31  InvalidTopUp

test result: ok. 80 passed; 0 failed

Full suite:

cargo test -p fluxora-stream
test result: ok. 503 passed; 0 failed

Acceptance criteria

Criterion Status
CI fails on changed existing discriminant numbers discriminant_fixture_matches_source fails on any = N change
New errors have exact regression tests every reachable variant has a try_* path test
New errors have documentation fixture table is the documented append registry with instructions
No existing tests closed/deleted/weakened 503 tests pass; only additions

Scope

No behaviour changes, no refactors, no dependency upgrades. Purely additive test infrastructure as required by the issue.

…h tests

Error discriminants are part of the public ABI — a client decodes an
on-chain Error(Contract, #N) against this table, and renumbering a variant
silently breaks every integration that relied on that number.

Before:
- error.rs had explicit = N values for all 31 variants, but there was no
  test enforcing those values. A developer could renumber a variant and the
  test suite would not notice.

After:
- contracts/stream/src/test/error_discriminants.rs adds:
  1. DISCRIMINANT_FIXTURE — a const table mapping every variant name to its
     frozen u32 value. Adding a new variant requires appending a row here;
     changing an existing number causes discriminant_fixture_matches_source
     to fail, which is the intended CI gate.
  2. discriminant_fixture_is_complete_and_contiguous — asserts the table
     covers discriminants 1..=LAST_DISCRIMINANT with no gaps, catching
     authoring errors in the fixture itself.
  3. discriminant_fixture_matches_source — casts every Error variant to u32
     at runtime and compares against the fixture. Any renumbering in error.rs
     fails this test immediately.
  4. Public error-path tests — every error variant reachable through a try_*
     client call is driven to that error at least once. Variants that cannot
     be produced via a public try_* path in the test host (TokenMissing,
     MalformedStreamId, StreamIdExhausted, TokenTransferFailed, InvalidTopUp)
     are confirmed by discriminant-cast assertions with explanatory comments.

Verification:
  cargo test -p fluxora-stream error -- --nocapture
  (prints the full 31-variant fixture table; 80/80 tests pass)

Full suite: 503 tests, 0 failed.

Closes Fluxora-Org#1535
@drips-wave

drips-wave Bot commented Aug 31, 2026

Copy link
Copy Markdown

@ValJnr-dev1 Great news! 🎉 Based on an automated assessment of this PR, the linked Wave issue(s) no longer count against your application limits.

You can now already apply to more issues while waiting for a review of this PR. Keep up the great work! 🚀

Learn more about application limits

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.

Make stream error discriminants append-only and fixture-checked

2 participants