audit: security + code-health fixes (13 findings, verified) - #2
Merged
Conversation
…SV export [DONATIONS-003]
…S-014, DONATIONS-030]
…ripe webhook, and monthly intents [DONATIONS-019, DONATIONS-020, DONATIONS-010]
… releasing a live lockout [DONATIONS-017]
…equestTimeout [DONATIONS-018, DONATIONS-021]
…the receipt subject [DONATIONS-023]
…rived over TLS [DONATIONS-012]
…nor-data action [DONATIONS-011]
…rong ones [DONATIONS-044]
…e, lock the data dir to 0700 [DONATIONS-041, DONATIONS-042, DONATIONS-027, DONATIONS-028]
…it SHA [DONATIONS-004]
…promise rejection [DONATIONS-043, DONATIONS-029]
…selves [DONATIONS-052] Also corrects CLAUDE.md §11, which specified argon2 for the admin password where the implementation has always used scrypt [DONATIONS-046].
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Security and code-health audit of 2026-08-03. 13 fixes, all verified. Full report in
docs/audit/SECURITY_AUDIT.md; what shipped and how it was checkedin
docs/audit/REMEDIATION.md.Why this is a PR and not a push to
mainA push to
maintriggersbuild-image.yml, which republishesghcr.io/openmasjid-solutions/openmasjiddonations:0.38.0and:latest— the live production tagthe App Store catalog's digest pin resolves to. That is a published artifact, so autonomous push was
disabled and everything came here instead.
Highest-value fix
DONATIONS-003 (High) — the donor-PII CSV export had no
Cache-Controlat a.csvURL..csvis in Cloudflare's default cached-extension list, so on a publicly-tunnelled install the edgecould have served every donor's name and email to a request carrying no session cookie.
Behaviour changes to watch (Tier 2)
Secureon HTTPS. It follows the request scheme, so plain-HTTP LANinstalls are unaffected — that was the design constraint, since always-
Securelocks a masjid outof its own panel. Revert
70d5457first if HTTPS admins report sign-in trouble.audit_logtable (additive,CREATE TABLE IF NOT EXISTS, reverse migration inREMEDIATION.md) plus the admin's username now carried inside the signed session token.
unhandledRejectionno longer kills the process — it logs and keeps serving.Verification
130 → 171 tests, 0 failures.Typecheck, build and web build clean on every commit, not just at theend. Server
npm audit4 high → 1 high (the remaining one is a two-major@fastify/staticbump thatthe adversarial pass refuted as exploitable in this configuration); web 1 high → 0.
Two regression tests were proven to fail against the pre-fix code and pass after — the login-limiter
sweep (2 failures before) and the email header injection (1 before). Real output is pasted in
REMEDIATION.md.
Two defects my own new tests caught in my own fixes are recorded there too, because they are the
argument for having written them: an audit-log ordering bug (same-millisecond rows tie-broke on
random hex) and a
connectionTimeoutthat would have reaped healthy keep-alive sockets.One thing to do before merging
The Action SHA pins (
73086c5) were verified by API but not executed —build-image.ymlonlyruns on
main,v*tags andworkflow_dispatch, so a PR never exercises it. Pleaseworkflow_dispatchit once on this branch first.Not fixed, deliberately
7 findings need a decision or a runtime I don't have (non-root container, base-image digests, CSP,
the
/api/setupoutage window, the ingress rate-limit bucket, anonymous-donation policy, tunneltoken via env). All in
docs/audit/ACTION_REQUIRED.mdwith myrecommendation for each. Nothing was marked fixed that I could not verify.