Skip to content

fix: fail closed on invalid score evidence - #139

Open
darcszn wants to merge 1 commit into
Gryd-lock:mainfrom
darcszn:fix/invalid-score-failure-closed
Open

fix: fail closed on invalid score evidence#139
darcszn wants to merge 1 commit into
Gryd-lock:mainfrom
darcszn:fix/invalid-score-failure-closed

Conversation

@darcszn

@darcszn darcszn commented Aug 30, 2026

Copy link
Copy Markdown

Summary

This PR closes a failure mode in the destination-risk review path: invalid, missing, or out-of-range risk evidence could be treated as a valid low-risk score instead of a degraded/unknown state. This was a security-sensitive issue because the extension is designed to fail closed when evidence is unavailable or untrusted.

The fix enforces a strict contract for risk scores and ensures that any malformed or unavailable oracle result is never presented as “safe.” In practice, this prevents the UI and signing review flow from silently converting degraded evidence into a low-risk destination.

Root cause

The risk tiering logic and legacy score flow were still allowing sentinel and invalid numeric values to pass as legitimate results:

  • negative values such as -1
  • NaN
  • infinity / non-finite values
  • out-of-range values outside 0..100
  • fractional or non-integer values

Those values were either being passed through as scores or normalized into low-risk buckets, which undermined the fail-closed model. The result was that a missing or malformed oracle response could look like a safe destination rather than an unknown or unavailable assessment.

What was changed

1) Strict score validation and fail-closed tier policy

  • Added explicit validation for risk scores before they are treated as valid evidence.
  • Only finite integer values between 0 and 100 are accepted as scored results.
  • Any invalid, missing, or out-of-range result is mapped to an unscored/unknown state instead of a low-tier rating.

This change was applied in the shared tiering logic and in the review outcome path so the behavior is consistent across the extension.

2) Review path no longer interprets invalid evidence as low risk

  • The review outcome resolution path now preserves invalid values as non-scored evidence instead of converting them to a low-risk result.
  • This prevents failure cases from being collapsed into an apparently “safe” outcome.

3) Protection status degrades correctly when health checks are unavailable

  • The protection status panel was hardened so missing bridge/worker health checks render a degraded state instead of presenting a healthy or “unknown but okay” result.
  • This ensures the user is explicitly told the protection path is unavailable rather than being left with a false sense of safety.

4) Regression coverage for the real issue

  • Added tests covering:
    • invalid score values not mapping to low risk
    • out-of-range scores being treated as unscored
    • oracle failure paths preserving the degraded state
    • protection status failure closed behavior

Why this matters

This is a safety boundary. A destination should never be presented as low risk when the evidence is malformed, unavailable, stale, or otherwise untrusted. The extension is intended to review security-sensitive transactions conservatively, so failing closed is the correct behavior when risk evidence cannot be trusted.

Validation

This change was verified with the project’s required checks:

  • npx vitest run --reporter=basic
  • npm run lint
  • npm run build

All passed.

closes #125

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.

Epic — Build an authenticated, privacy-preserving risk-oracle protocol with explicit uncertainty

1 participant