1. Purpose
This policy defines how a change reaches production. It is deliberately short and entirely enforced by automation: a process that depends on people remembering is a process that reports success while doing nothing.
2. Lifecycle
| Stage | What happens | Enforced by |
|---|---|---|
| Design | Security-relevant changes — anything touching authentication, biometric data, tenancy or evidence — are designed against the documented architecture before implementation. | Review |
| Implement | Work happens on a branch. Direct commits to main are avoided; changes land through pull requests. | Pull request workflow |
| Verify | Type checking, linting, unit and integration tests, and a production build run on every push and pull request. | CI workflow |
| Scan | Static analysis, dependency audit and secret scanning run on every pull request and weekly on a schedule. | Security workflow |
| Review | A human reviews the diff, the scan results and the test evidence. | Pull request review |
| Release | Database migrations are applied before the application is deployed. Migrations must be additive. | CI guard + runbook |
| Verify in production | Health, security headers and key endpoints are checked after every deploy. | Deployment checklist |
3. Automated gates
| Gate | Tool | When | On failure |
|---|---|---|---|
| Static application security testing | GitHub CodeQL, security-extended query suite | Every PR and push; weekly | Findings raised as code-scanning alerts |
| Dependency audit | npm audit | Every PR and push; weekly | Build fails on high or critical in runtime dependencies |
| Secret scanning | gitleaks, full git history | Every PR and push; weekly | Build fails |
| Dynamic application security testing | OWASP ZAP baseline | Weekly and on demand against the running service | Report reviewed; failures triaged |
| Type safety | TypeScript, no implicit any escape | Every PR and push | Build fails |
| Lint | ESLint with eslint-plugin-security | Every PR and push | Build fails |
| Tests | Vitest — unit and integration | Every PR and push | Build fails |
| Migration safety | Custom CI check | Every PR and push | Build fails on destructive DDL |
| Dependency currency | Dependabot | Weekly | Pull request raised |
4. Separation of duties and change control
- Production secrets are stored in the platform secret store. They are write-only: they cannot be read back, including by the engineers who set them.
- Secrets are never committed. The repository ignores local secret files, and secret scanning covers the full history.
- Every production change is traceable to a commit, and every commit to a pull request.
- Emergency fixes follow the same pipeline; the pipeline is fast enough that bypassing it is never justified.
5. Data handling in development
- Production biometric data is never copied to a development environment.
- Local and staging environments use synthetic data, including a built-in simulator that generates synthetic meeting participants so the product can be exercised end to end without real personal data.
- Development environments use their own encryption keys, never production keys.
6. Review
This policy is reviewed annually, and whenever the pipeline materially changes.