Test seed data loader¶
| ID | MOD-158 |
| System | SD07 |
| Repo | bank-platform |
| Build status | Deployed |
| Deployed | Yes |
| Last commit | c27bc7a |
Purpose¶
MOD-158 loads deterministic seed data into the dev and UAT Neon databases on first deploy to a fresh stage. It ensures that every integration test has a realistic baseline to work against — customers with known identities, accounts with balances, chart of accounts, GL configuration, and service credentials for test runners.
Without this module, each team member standing up a new dev environment or the CI pipeline deploying to a fresh UAT stage would start with an empty database. Modules with integration tests that depend on pre-existing customers, accounts, or GL entries would fail immediately. Data loading would become a manual, inconsistent, and often forgotten step.
Architecture¶
The seed loader runs as an AWS Lambda function invoked by an SST Custom Resource during sst deploy. The deployment sequence is:
- SST deploys MOD-158 resources (Lambda function, IAM role, DynamoDB version table)
- SST Custom Resource triggers the seed Lambda
- Lambda checks
/{repo}/{stage}/seed-versionin SSM - If current version is already recorded → exit immediately (idempotent)
- If not → load the seed profile for the stage, then write the version key
Re-running sst deploy does not reload seed data because the version key is already present. Resetting requires an explicit operator command (pnpm run seed:reset --stage {stage}), which truncates seed tables and removes the version key before re-running.
Seed profiles¶
dev profile (10 customers, ~20 accounts)¶
| Customer | Jurisdiction | eIDV outcome | Sanctions |
|---|---|---|---|
| CUST-D001 to CUST-D005 | NZ | PASS | Clear |
| CUST-D006 to CUST-D008 | AU | PASS | Clear |
| CUST-D009 | NZ | FAIL | Clear |
| CUST-D010 | NZ | PASS | HIT (SANCTIONED) |
Each passing customer has one everyday account and one savings account. Balances range from NZD/AUD 2,000 to 50,000. All accounts are in Active state. Chart of accounts (100-series GL codes) and interest rate schedule (standard product rates) are also loaded.
A service account credential (scoped JWT) for integration test runners is written to Secrets Manager at /bank-{repo}/dev/test-runner/jwt.
uat profile (100 customers, ~250 accounts)¶
Superset of the dev profile, extended with: - 90 customers with realistic NZ and AU demographics (names, DOBs, addresses generated deterministically from seed 20260427) - Account types: everyday, savings, notice (30-day and 90-day), term deposit (3-month and 12-month) - 90 days of pre-loaded transaction history (bulk INSERT, not processed through the event pipeline) - Accounts in edge states: one dormant (last transaction > 24 months ago), one pending KYC review (CDD tier upgrade triggered), one restricted (sanctions hit pending adjudication) - Full product instance records (PRD-001 through PRD-005)
Neon branch mapping¶
| Stage | Neon branch | Provisioned by | Persists across deploy |
|---|---|---|---|
| dev | dev |
MOD-103 | Yes |
| uat | uat |
MOD-103 | Yes |
| prod | main |
MOD-103 | Yes |
The UAT Neon branch is never torn down by SST. Accumulated synthetic transaction history (from MOD-159) persists until an explicit seed:reset is run. This is intentional — UAT should look like an operating bank with history.
Version key¶
The SSM key /{repo}/{stage}/seed-version holds the semver string of the last successfully loaded seed profile (e.g. 1.0.0). When the seed loader code changes in a way that requires a reload, the version constant in src/seed-version.ts is bumped. On the next deploy, the Lambda detects the version mismatch and reloads.
Patch bumps reload seed data. Minor bumps add new data without truncating. Major bumps truncate and reload from scratch.
Scope¶
MOD-158 is deployed to dev and uat stages only. Like MOD-157, the sst.config.ts skips all resource provisioning when stage === 'prod'.
Module dependencies¶
Depends on¶
| Module | Title | Required? | Contract | Reason |
|---|---|---|---|---|
| MOD-103 | Neon database platform bootstrap | Required | — | Neon database branches (dev and UAT) must be provisioned before seed data can be loaded into them. |
| MOD-043 | EventBridge domain event governance | Required | — | EventBridge schema registry entries for seed customers and accounts are registered by MOD-158; the registry must exist. |
| MOD-045 | Secrets & key management | Required | — | Seed data loader reads Neon connection strings from Secrets Manager; MOD-045 must have provisioned the secrets path before loading begins. |
| MOD-157 | External provider stub service | Required | — | Seed identities are designed to trigger known stub outcomes; MOD-157 must be deployed so that stub SSM paths exist before the loader writes cross-references. |
Required by¶
| Module | Title | As | Contract |
|---|---|---|---|
| MOD-159 | Synthetic transaction engine | Hard dependency | — |
| MOD-160 | Cross-module acceptance suite | Hard dependency | — |
Policies satisfied¶
(No policies assigned)
Capabilities satisfied¶
(No capabilities mapped)
Part of SD07 — Data Platform & Governance Infrastructure
Compiled 2026-05-22 from source/entities/modules/MOD-158.yaml