Renamed scripts/create-ssp.mjs -> create-frontend.mjs (+ its WP-45 doc, npm
script, and every prose/command reference) since "ssp" reads as an acronym
where "create-frontend" says what it does.
Also fixes two real bugs found while running it for real during WP-61:
scripts/ci-local.sh was missing from RENAME_CONTENT_FILES (any --name'd
clone that keeps a backend would break `npm run ci`, still hardcoding
BigRegister.slnx), and plopfile.mjs's `gen:context` insertion into
.dependency-cruiser.js anchored on the `showcase: null,` line, which
create-ssp/create-frontend has already stripped by the time gen:context
runs in the same invocation — silently leaving a freshly scaffolded
context with no CONTEXT_ALLOWED fence entry at all. Re-anchored on the
`const CONTEXT_ALLOWED = {` line instead, which never moves.
Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
107 lines
6.9 KiB
Markdown
107 lines
6.9 KiB
Markdown
---
|
||
name: new-ssp
|
||
description: Bootstrap a new self-service portal from this repo as a template — what to keep, strip, rename, and re-seed. Use when starting a new SSP for a different domain/register.
|
||
---
|
||
|
||
# New SSP from this template
|
||
|
||
The template's value is the **enforced architecture** (layer fences, token gate,
|
||
a11y gate, API-drift gate) and the shared building blocks — not the BIG-register
|
||
business content. Keep the machinery, replace the domain.
|
||
|
||
## Run the script
|
||
|
||
Clone this repo, `npm ci`, then mechanise the mechanical parts (WP-45):
|
||
|
||
```bash
|
||
node scripts/create-frontend.mjs --name Kvk --context inschrijving
|
||
```
|
||
|
||
`--name` (PascalCase) replaces `BigRegister.*` everywhere; `--context` (lowercase Dutch
|
||
ubiquitous term) is passed straight to `gen:context` (`plop context`, WP-44) to seed the new
|
||
portal's first real context. Add `--dry-run` to preview file operations first, `--keep
|
||
<context>` to leave one business context in place temporarily as a worked example, and
|
||
`--skip-backend` if no .NET SDK is available yet (skips `gen:api`).
|
||
|
||
It strips the four business contexts and their wiring, renames the backend, re-runs
|
||
`gen:api`, and seeds the first context — then **prints a checklist** for what it deliberately
|
||
doesn't script: backend business rules and real branding can't be generated from nothing.
|
||
Work through that checklist, keeping the GREEN gate below passing at every step.
|
||
|
||
## Keep as-is
|
||
|
||
- `src/app/shared/` — kernel (`fp.ts`), application (`remote-data`, `store`,
|
||
`submit`), ui atoms/molecules, layout templates, upload subtree — **except**
|
||
`shared/ui/debug-state/`, which the script deletes (see below).
|
||
- Tooling: `eslint.config.mjs`, `.dependency-cruiser.js` (edited by the script, not
|
||
hand-stripped — see below), `scripts/check-tokens.sh`, `.github/workflows/ci.yml`,
|
||
`nswag.json`, `.storybook/`, `proxy.conf.json`, `.npmrc` (`legacy-peer-deps` —
|
||
and never `npm audit fix --force`, it downgrades Angular).
|
||
- `src/app/auth/` (fake auth shell) and `src/app/shared/infrastructure/scenario.interceptor.ts` (dev-only).
|
||
- `docs/reference/architecture/` ADRs 0001–0003 — the decisions still apply; amend, don't delete.
|
||
- `CLAUDE.md`, `docs/reference/architecture/ARCHITECTURE.md`, `docs/reference/fp-tea-atomic-design.md` — update names/examples as contexts change.
|
||
- `.claude/skills/` — these recipes are the point of the template.
|
||
- `src/app/beheer/` — its frontend is genuinely generic (data-driven off a `StamdataTable`/
|
||
`AuditEntry` shape, nothing BIG-specific). Its _backend_ Stamdata catalog is not — see below.
|
||
|
||
## Strip / replace — what the script does
|
||
|
||
- Business contexts `registratie/`, `herregistratie/`, `brief/`, `showcase/`: deleted (or one
|
||
kept temporarily via `--keep` as the worked example while building the first real context —
|
||
**new-context** + **new-feature** skills; if kept, update the worked-example paths in those
|
||
skills to the new flagship context once you drop it for real).
|
||
- `app.routes.ts` route blocks and `tsconfig.json` aliases for removed contexts, and their
|
||
`CONTEXT_ALLOWED` entry in **`.dependency-cruiser.js`** — boundary rules moved there in
|
||
WP-38 and are no longer in `eslint.config.mjs` (which only keeps `no-explicit-any` + a11y
|
||
template rules). Route stripping matches on the _import alias_ a route uses, not its own
|
||
path segment — `beheer/zaken` imports `@registratie/ui/admin-cases.page` and gets dropped
|
||
along with `registratie` even though its own path doesn't say so.
|
||
- `src/app/shared/ui/debug-state/` (the dev `⚙ state` panel): imports
|
||
`@registratie/application/big-profile.store` directly and is the one path
|
||
`.dependency-cruiser.js`'s `shared-no-features` rule exempts — there's no generic way to
|
||
re-target it at an arbitrary new context, so it's deleted alongside `registratie`, along
|
||
with its three wiring lines in `shell.component.ts` (import, `imports:` entry, template tag).
|
||
- The `dashboard` route is **not** deleted even though it currently imports
|
||
`@registratie/ui/dashboard.page` — too much else hardcodes `/dashboard` (login's post-auth
|
||
redirect, `authGuard`'s fallback, header nav/logo, breadcrumb trail, several stories/specs).
|
||
The script rewrites its `loadComponent` to point at the freshly scaffolded `--context` page
|
||
instead (a `TODO(create-frontend)` stopgap landing page, not a real overview).
|
||
- `scripts/gen-snippets.mjs` (showcase-only) + its `package.json` script entry + its CI/
|
||
`ci-local.sh` "showcase snippets drift" steps: deleted alongside `showcase/` — they run
|
||
unconditionally, so leaving them breaks `npm run ci` immediately once `showcase/` is gone.
|
||
- Backend: keep the skeleton (`Program.cs` minimal-API style, ProblemDetails 422,
|
||
`X-Correlation-Id` audit line, `/api/v1` versioning, `Contracts/`/`Domain/`/`Data/`
|
||
split, test project, and the generic `Stamdata/StamdataFile.cs`+`StamdataTable.cs`
|
||
reflection-driven `/stamdata` endpoint machinery, ADR-0004) — replace `Data/SeedData.cs`,
|
||
`Domain/*` rules, `Contracts/*` DTOs, and the three concrete Stamdata catalog entries
|
||
(`Beroep`/`Opleiding`/`Specialisme`/`ProfessionMapping` + their JSON) with the new
|
||
register's. The script renames the solution/projects from `BigRegister.*` (and updates
|
||
`package.json`'s `gen:api`, `ci.yml`'s paths, `docker-compose.yml`) — it does not rewrite
|
||
business content; that's the printed checklist.
|
||
- Regenerate the seam: `npm run gen:api` (commits `backend/swagger.json` +
|
||
`src/app/shared/infrastructure/api-client.ts`) — only reflects a new shape once the backend
|
||
content above is actually rewritten.
|
||
- Branding: the script swaps `src/index.html`'s stylesheet `<link>` + `<title>` to a
|
||
placeholder path and creates an empty `public/<name>-huisstijl/` — it cannot generate a
|
||
real house style. Vendor your CSS there, then re-point the `--rhc-*` bridge in
|
||
`src/styles.scss` (ADR-0003 pattern: bridge, don't rewrite tokens), then `npm run check:tokens`.
|
||
- `docs/project/backlog/` WPs, PRDs, and memory-specific docs — new portal, new backlog
|
||
(keep `docs/project/backlog/README.md`'s WP process/template if you like the workflow).
|
||
`docs/reference/scaffolding.md` also names `BigRegister.Api` in prose — update by hand.
|
||
- `e2e/*.spec.ts` (`smoke.spec.ts`, `brief-v2.spec.ts`, `error-state.spec.ts`): full
|
||
BIG-register user-flow tests (BSN login → registration wizard → submission assertions).
|
||
Not touched by the script (they don't block `npm run ci` — the `e2e` job runs separately)
|
||
but are 100% stale business content; rewrite once you have real flows to test.
|
||
|
||
## Verify — the GREEN gate must pass at every step
|
||
|
||
```bash
|
||
npm run lint && npm run check:tokens && npm test && npm run build
|
||
npm run build-storybook && npm run test-storybook:ci
|
||
cd backend && dotnet test && cd ..
|
||
npm run gen:api && git diff --exit-code backend/swagger.json src/app/shared/infrastructure/api-client.ts
|
||
```
|
||
|
||
Or just `npm run ci` for the non-storybook subset. Strip incrementally and keep this green
|
||
— the fences are only worth having if they never go red.
|