Security
Written for someone who will check.
This page assumes a technical reader and does not soften anything. Where a control is designed but not yet running, it says so — including the one that would have been easiest to overstate.
The controls
What holds the record together.
- Tenant isolation
- Enforced in the database, not in application code. A deliberate cross-tenant read must fail, or the build does not pass.
- Append-only audit log
- No one can edit it. Not us, not the application. Every access writes a row that cannot be updated or deleted. CI proves the constraint holds.
- Encryption
- TLS in transit, encrypted at rest. Keys live in a managed key service, so rotation is an infrastructure operation, not a deploy.
- Consent-scoped access
- A request outside the consent artefact is refused, not trimmed. Access is scoped to the clinic, the practitioner, and the artefact that authorised it. Refusals are logged.
- Authentication
- One boundary handles every session. Credentials are per tenant, sessions are short-lived, and the browser never talks to the API directly.
- Data residency
- India only — written and checked, not yet live. The mechanism is below. It has never been applied to a production account, and we say so.
- Backup and restore
- The restore drill is performed, not documented. Point-in-time recovery on the database. A backup nobody has restored is a hypothesis.
- Vulnerability disclosure
- Tell us. No NDA required. We would rather hear it from you than from a reviewer. There is a published address for it.
India only
Where the records live.
Residency is the claim most easily made and least often enforced, so here is the mechanism rather than the assurance.
- 01 The cloud account denies every non-Indian region at the organisation level, keyed on the region of the request itself — not on developers remembering to pick the right one.
- 02 A trail watches the regions we do not use, because that is where a denied call would appear, and a denied out-of-region call raises an alarm rather than a log line.
- 03 A check in CI fails the build if any non-Indian region is named anywhere in our infrastructure code, or if those controls are removed from it.
Present tense
What is true today.
The same table as the ABDM page, from one source, so the two cannot drift apart. A posture table with no unfinished rows has not been written honestly.
| Control | State | How it is established |
|---|---|---|
| FHIR R4 boundary mapping | Implemented | Projection table in `libs/abdm`, covered by offline tests. No network dependency. |
| ABDM gateway isolation | Implemented | `abdm-gw` is a separate deployable; module boundaries are enforced by a CI lint rule. |
| Gateway configuration | Planned | No endpoint, client id or profile URI exists in our codebase. The config reports its own absence rather than defaulting. |
| Append-only audit log | Implemented | Every record access writes a row that cannot be updated or deleted; a CI check proves it. |
| Tenant isolation | Implemented | Row-level security in Postgres, with a cross-tenant read test that must fail to pass. |
| Data residency — India only | Authored, not deployed | An Organizations SCP keyed on `aws:RequestedRegion`, plus a multi-region CloudTrail and an alarm on denied out-of-region calls. CI fails if any non-Indian region is named anywhere in the infrastructure code. Not yet applied — no production account exists. |
| Safe-to-Host certificate | Planned | Requires an audit by a STQC or CERT-In empanelled agency. Not yet commissioned; no date is claimed. |
Practising it here
This website, too.
A site that describes a security posture and then fails a public header check has handed a reviewer a contradiction. So this one is built to the same standard as the thing it describes.
- A content security policy with no
unsafe-inlineand nounsafe-eval. The single inline script this site needs — the one that sets your theme before the page paints — is allowed by cryptographic hash. The hash is recomputed from the built output on every build and checked again by a verification script, so it cannot silently go stale. - No third-party requests. The fonts are self-hosted. There is no analytics script, no tag manager, no embedded widget, and nothing that would set a cookie. The site has no cookie banner because it has no cookies.
- Strict transport security, frame denial, and a referrer policy that does not leak the page you came from to anyone else.
- No form posts anywhere. The contact form composes a message in your own mail client; this site receives nothing and stores nothing.
Found something?
A dedicated disclosure address has not been published yet. Until it is, use the contact page and mark the message as a security report — it will be routed the same way.
Report it