Skip to content

[Bug] Fix 2 CodeQL high alerts surfaced in v0.9.0 (redemption-code modulo bias + SDK ReDoS regex) #757

Description

@chronoai-shining

CodeQL flagged 3 new alerts on the v0.9.0 develop → main promotion (#755). Both high alerts are low practical severity, so v0.9.0 shipped with a tracked follow-up (per maintainer decision) rather than blocking the release. This issue tracks the fixes.

1. High — modulo bias on crypto-random redemption codes

ornn-api/src/domains/redemption-codes/service.ts:127

out += REDEMPTION_CODE_ALPHABET[bytes[i]! % REDEMPTION_CODE_ALPHABET.length];

byte % 31 introduces a ~1.5% modulo bias (256 % 31). The code comments already acknowledge this as accepted for human-shareable promo codes (not security tokens; unique index + retry loop absorbs collisions). Still, it's a real high-rated finding.

Fix: use rejection sampling or crypto.randomInt(0, REDEMPTION_CODE_ALPHABET.length) per character to remove the bias. Keep existing generation tests green.

2. High — polynomial-backtracking regex in TS SDK

sdk/typescript/src/client.ts:70

this.baseUrl = options.baseUrl.replace(/\/+$/, "");

CodeQL flags \/+$ as polynomial ReDoS on "uncontrolled" input. In practice baseUrl is a developer-set config value and the TS SDK is not yet published (held for v1.0). Low exposure, but worth removing the backtracking shape.

Fix: drop the regex — strip trailing slashes with a non-regex loop/slice, or anchor a linear pattern. Add a unit test.

3. Medium/warning — workflow token permissions

.github/workflows/ci.yml:87 — add an explicit permissions: block (minimal contents: read) to the CI workflow.

Acceptance

  • Redemption-code generation is unbiased (rejection sampling / randomInt).
  • SDK baseUrl trailing-slash strip has no backtracking regex.
  • ci.yml declares an explicit permissions block.
  • CodeQL clean on the fix PR.

Related: shipped in v0.9.0 (#753).

Metadata

Metadata

Labels

apiAPI design & endpointsbugSomething isn't workingpriority:P1High. Should be done this cycle.sdkTypeScript / Python client SDKssecuritySecurity & trustsize:SSmall: < ~1h, single file/concern. Size is informational.status:donePR merged to develop-auto. Issue closed by Closes #N.type:bugDefect: behavior diverges from intent/spec.

Type

No type

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions