QA: Verify invariants, business logic, and automated tests #1

Closed
opened 2026-04-20 12:12:40 +00:00 by PlasticDigits · 11 comments
PlasticDigits commented 2026-04-20 12:12:40 +00:00 (Migrated from gitlab.com)

Scope

Validate ust1-window against documented invariants and expected behavior, and confirm the test suite and tooling pass in a clean checkout.

Environment prep

  • Clone repo and use branch under test (typically main).
  • Rust stable with rustfmt + clippy components.
  • Optional: python3 -m venv .venv and pip install -r requirements-dev.txt for pre-commit.

Commands (must all succeed)

  • cargo fmt --all -- --check
  • cargo clippy --all-targets -- -D warnings
  • cargo test (full workspace)
  • pre-commit run --all-files (if pre-commit installed)

Invariants — ust1-common / math (INV-MATH-001, INV-SWAP-001, INV-SWAP-002)

  • RATE_SCALE (1e18) semantics: rate R means R/RATE_SCALE FDUSD per 1 vFDUSD; spot-check forward vFDUSD → UST1 and reverse UST1 → vFDUSD formulas match ust1-common/src/math.rs.
  • Fee 50 bps on the UST1 leg only: output strictly below notional when fee applies; no fee drift vs DEFAULT_FEE_BPS.

Invariants — oracle policy (INV-ORACLE-THROTTLE-001, INV-ORACLE-DAILY-001, INV-ORACLE-MONO-001)

  • Monotonicity: on-chain stored rate never decreases on UpdateRate (only flat or increase).
  • 4h throttle: second update within 4h of a successful last_update_sec is rejected (unless last_update_sec == 0 for first post-init edge — confirm against spec intent).
  • UTC daily +2% cap: within a UTC calendar day, proposed rate must not exceed day_baseline_rate * 1.02 (baseline updated at UTC day rollover per contract).
  • Off-chain parity: ust1_common::oracle_policy::check_rate_update matches contract behavior (service and tests rely on this).

Invariants — window (INV-LIMIT-001)

  • Per-tx UST1 cap enforced on minted UST1 (deposit) and gross UST1 in (withdraw), per ust1-window config.
  • Rolling 24h UST1 cap: counter resets when window_start_sec == 0 or after 24h; double-count at boundary is acceptable per product note — confirm behavior is intentional.

Business logic — contracts

  • Oracle: only oracle_operator may UpdateRate; governance can rotate operator, pause, two-step governance transfer.
  • Window: only expected cw20 senders (vfdusd_token, ust1_token); Deposit / Withdraw hooks behave as documented; pause blocks swaps.
  • cw20-mintable: window is minter on UST1; burns/transfers align with deposit/withdraw paths.
  • make start + make wait-healthy (LocalTerra).
  • After wasm deploy (see scripts/): one vFDUSD→UST1 deposit and one UST1→vFDUSD withdraw on local net.

CI parity

  • Same checks as GitHub/GitLab CI: format, clippy, tests; gitleaks / secret scanning where configured (.gitleaks.toml, .gitlab-ci.yml secret-detection template).

Sign-off

  • All items above checked or waived with note.
  • List commit SHA verified and any deviations documented in comments.
## Scope Validate **ust1-window** against documented invariants and expected behavior, and confirm the test suite and tooling pass in a clean checkout. ## Environment prep - [ ] Clone repo and use branch under test (typically `main`). - [ ] Rust stable with `rustfmt` + `clippy` components. - [ ] Optional: `python3 -m venv .venv` and `pip install -r requirements-dev.txt` for pre-commit. ## Commands (must all succeed) - [ ] `cargo fmt --all -- --check` - [ ] `cargo clippy --all-targets -- -D warnings` - [ ] `cargo test` (full workspace) - [ ] `pre-commit run --all-files` (if pre-commit installed) ## Invariants — `ust1-common` / math (`INV-MATH-001`, `INV-SWAP-001`, `INV-SWAP-002`) - [ ] **RATE_SCALE (1e18)** semantics: rate `R` means `R/RATE_SCALE` FDUSD per 1 vFDUSD; spot-check forward `vFDUSD → UST1` and reverse `UST1 → vFDUSD` formulas match `ust1-common/src/math.rs`. - [ ] **Fee 50 bps** on the UST1 leg only: output strictly below notional when fee applies; no fee drift vs `DEFAULT_FEE_BPS`. ## Invariants — oracle policy (`INV-ORACLE-THROTTLE-001`, `INV-ORACLE-DAILY-001`, `INV-ORACLE-MONO-001`) - [ ] **Monotonicity**: on-chain stored rate never decreases on `UpdateRate` (only flat or increase). - [ ] **4h throttle**: second update within 4h of a successful `last_update_sec` is rejected (unless `last_update_sec == 0` for first post-init edge — confirm against spec intent). - [ ] **UTC daily +2% cap**: within a UTC calendar day, proposed rate must not exceed `day_baseline_rate * 1.02` (baseline updated at UTC day rollover per contract). - [ ] **Off-chain parity**: `ust1_common::oracle_policy::check_rate_update` matches contract behavior (service and tests rely on this). ## Invariants — window (`INV-LIMIT-001`) - [ ] **Per-tx UST1 cap** enforced on minted UST1 (deposit) and gross UST1 in (withdraw), per `ust1-window` config. - [ ] **Rolling 24h UST1 cap**: counter resets when `window_start_sec == 0` or after 24h; double-count at boundary is acceptable per product note — confirm behavior is intentional. ## Business logic — contracts - [ ] **Oracle**: only `oracle_operator` may `UpdateRate`; governance can rotate operator, pause, two-step governance transfer. - [ ] **Window**: only expected cw20 senders (`vfdusd_token`, `ust1_token`); `Deposit` / `Withdraw` hooks behave as documented; pause blocks swaps. - [ ] **cw20-mintable**: window is minter on UST1; burns/transfers align with deposit/withdraw paths. ## Integration / manual smoke (optional but recommended) - [ ] `make start` + `make wait-healthy` (LocalTerra). - [ ] After wasm deploy (see `scripts/`): one vFDUSD→UST1 deposit and one UST1→vFDUSD withdraw on local net. ## CI parity - [ ] Same checks as GitHub/GitLab CI: format, clippy, tests; **gitleaks** / secret scanning where configured (`.gitleaks.toml`, `.gitlab-ci.yml` secret-detection template). ## Sign-off - [ ] All items above checked or waived with note. - [ ] List commit SHA verified and any deviations documented in comments.
PlasticDigits commented 2026-04-20 12:12:41 +00:00 (Migrated from gitlab.com)

assigned to @Brouie

assigned to @Brouie
Brouie commented 2026-04-21 08:22:52 +00:00 (Migrated from gitlab.com)

@PlasticDigits initial verification pass on 52e4d41 (or current main).

Test baseline

cargo test --workspace on QA server:

  • ust1-common: 7/7 pass (includes proptest invariant checks)
  • ust1-oracle unit: 7/7 pass
  • ust1-oracle multitest: 8/8 pass (INV-ORACLE-THROTTLE/DAILY/MONO + pause/ACL + governance)
  • ust1-window multitest: 6/6 pass (INV-LIMIT-001 + pause/ACL + invalid cw20 sender + below-min)
  • ust1-integration-tests: 0 scaffold (no tests defined yet)

Total: 28/28 pass, 0 failures.

Invariants → test coverage

Invariant Source Test
INV-MATH-001 ust1-common/src/lib.rs inv_math_001_one_to_one_rate ✅
INV-MATH-002 ust1-common/src/lib.rs prop_fee_never_inverts (proptest) ✅
INV-SWAP-001 math.rs + window multitest + integration inv_swap_001_fee_reduces_output, E2E deposit ✅
INV-SWAP-002 math.rs module doc No explicitly-tagged test ⚠️
INV-ORACLE-THROTTLE-001 oracle_policy + oracle multitest + integration:445 ✅
INV-ORACLE-DAILY-001 oracle_policy + oracle multitest:182 + integration:358 ✅
INV-ORACLE-MONO-001 oracle_policy + oracle multitest:127 + state.rs:22 ✅
INV-LIMIT-001 window state.rs + window multitest + integration ✅

Coverage gap

INV-SWAP-002 (reverse: UST1 → vFDUSD math) is documented in math.rs module comments but has no test specifically tagged INV-SWAP-002. The withdraw path is exercised in ust1-window multitest (withdraw_below_min_vfdusd_out_rejected, withdraw_insufficient_vfdusd_in_window) and the proptest prop_fee_never_inverts touches fee math in both directions, but nothing asserts ust1_after_fee_to_vfdusd conforms to the documented formula floor(u * (BPS_DENOM - fee_bps) / BPS_DENOM * RATE_SCALE / R) on known vectors. Recommend adding a unit test pattern-matching inv_swap_001_fee_reduces_output for the reverse direction with known input/output pairs.

Related: this is informational, not a bug. Filing as part of #2 (expand coverage) rather than a separate security issue.

Cross-ref

Pairs with the 9 security findings filed under #5 — those cover behavioral/operational risk. This issue (#1) is baseline test health, which is currently green.

Verification complete for the current state. Will re-run on any contract change and report drift.

@PlasticDigits initial verification pass on 52e4d41 (or current main). ## Test baseline `cargo test --workspace` on QA server: - ust1-common: 7/7 pass (includes proptest invariant checks) - ust1-oracle unit: 7/7 pass - ust1-oracle multitest: 8/8 pass (INV-ORACLE-THROTTLE/DAILY/MONO + pause/ACL + governance) - ust1-window multitest: 6/6 pass (INV-LIMIT-001 + pause/ACL + invalid cw20 sender + below-min) - ust1-integration-tests: 0 scaffold (no tests defined yet) **Total: 28/28 pass, 0 failures.** ## Invariants → test coverage | Invariant | Source | Test | |---|---|---| | INV-MATH-001 | ust1-common/src/lib.rs | `inv_math_001_one_to_one_rate` ✅ | | INV-MATH-002 | ust1-common/src/lib.rs | `prop_fee_never_inverts` (proptest) ✅ | | INV-SWAP-001 | math.rs + window multitest + integration | `inv_swap_001_fee_reduces_output`, E2E deposit ✅ | | INV-SWAP-002 | math.rs module doc | **No explicitly-tagged test** ⚠️ | | INV-ORACLE-THROTTLE-001 | oracle_policy + oracle multitest + integration:445 | ✅ | | INV-ORACLE-DAILY-001 | oracle_policy + oracle multitest:182 + integration:358 | ✅ | | INV-ORACLE-MONO-001 | oracle_policy + oracle multitest:127 + state.rs:22 | ✅ | | INV-LIMIT-001 | window state.rs + window multitest + integration | ✅ | ## Coverage gap INV-SWAP-002 (reverse: UST1 → vFDUSD math) is documented in `math.rs` module comments but has no test specifically tagged INV-SWAP-002. The withdraw path is exercised in `ust1-window` multitest (`withdraw_below_min_vfdusd_out_rejected`, `withdraw_insufficient_vfdusd_in_window`) and the proptest `prop_fee_never_inverts` touches fee math in both directions, but nothing asserts `ust1_after_fee_to_vfdusd` conforms to the documented formula `floor(u * (BPS_DENOM - fee_bps) / BPS_DENOM * RATE_SCALE / R)` on known vectors. Recommend adding a unit test pattern-matching `inv_swap_001_fee_reduces_output` for the reverse direction with known input/output pairs. Related: this is informational, not a bug. Filing as part of #2 (expand coverage) rather than a separate security issue. ## Cross-ref Pairs with the 9 security findings filed under #5 — those cover behavioral/operational risk. This issue (#1) is baseline test health, which is currently green. Verification complete for the current state. Will re-run on any contract change and report drift.
Brouie commented 2026-04-21 08:26:21 +00:00 (Migrated from gitlab.com)

mentioned in issue #2

mentioned in issue #2
Brouie commented 2026-04-22 03:42:40 +00:00 (Migrated from gitlab.com)

mentioned in issue #18

mentioned in issue #18
Brouie commented 2026-04-22 03:43:00 +00:00 (Migrated from gitlab.com)

@PlasticDigits closing per today's dev review. Single outstanding coverage gap (INV-SWAP-002) split out as #18. Verification baseline from yesterday holds: 40/40 workspace tests pass, all INV-* mapped to tests except the one now tracked separately.

@PlasticDigits closing per today's dev review. Single outstanding coverage gap (INV-SWAP-002) split out as #18. Verification baseline from yesterday holds: 40/40 workspace tests pass, all INV-* mapped to tests except the one now tracked separately.
Brouie (Migrated from gitlab.com) closed this issue 2026-04-22 03:43:02 +00:00
PlasticDigits commented 2026-08-08 04:40:18 +00:00 (Migrated from gitlab.com)

mentioned in issue #22

mentioned in issue #22
PlasticDigits commented 2026-08-08 04:52:40 +00:00 (Migrated from gitlab.com)

mentioned in commit f312188dd1f8a7c61dc32de5647a58f3e041293e

mentioned in commit f312188dd1f8a7c61dc32de5647a58f3e041293e
PlasticDigits commented 2026-08-08 04:52:50 +00:00 (Migrated from gitlab.com)

mentioned in merge request !39

mentioned in merge request !39
PlasticDigits commented 2026-08-08 04:53:26 +00:00 (Migrated from gitlab.com)

mentioned in merge request !40

mentioned in merge request !40
PlasticDigits commented 2026-08-08 05:12:13 +00:00 (Migrated from gitlab.com)

mentioned in commit c1d19c7329

mentioned in commit c1d19c7329ab881724554a5cd015e0adb22c957e
PlasticDigits commented 2026-08-08 06:01:29 +00:00 (Migrated from gitlab.com)

mentioned in issue #27

mentioned in issue #27
Sign in to join this conversation.
No milestone
No project
No assignees
1 participant
Notifications
Due date
The due date is invalid or out of range. Please use the format "yyyy-mm-dd".

No due date set.

Dependencies

No dependencies set

Reference
code/ust1-window#1
No description provided.