78 lines
3.3 KiB
Markdown
78 lines
3.3 KiB
Markdown
# Starter experience contract
|
|
|
|
The repository provides a runnable, domain-neutral application rather than
|
|
only infrastructure contracts. The starter experience is intentionally
|
|
replaceable at the page level while the shell, providers, boundaries,
|
|
primitives, and state surfaces remain reusable.
|
|
|
|
## Runtime composition
|
|
|
|
```text
|
|
validated config + coherent release manifest
|
|
-> concrete adapters
|
|
-> QueryClientProvider
|
|
-> BrowserRouter
|
|
-> ThemeProvider
|
|
-> SessionProvider
|
|
-> AppShell
|
|
-> lazy route boundary
|
|
```
|
|
|
|
Boot stops before product mount when configuration or release coherence fails.
|
|
Each lazy page renders inside Suspense and a telemetry-aware route boundary.
|
|
Route changes move focus to the new page heading; the skip link and landmarks
|
|
remain stable in the shell.
|
|
|
|
## Registered routes
|
|
|
|
| ID | Path | Access | Surface |
|
|
| --- | --- | --- | --- |
|
|
| `APP_HOME` | `/` | public | readiness dashboard |
|
|
| `EXAMPLES_UI` | `/examples/ui` | public | interactive primitives and tokens |
|
|
| `EXAMPLES_STATES` | `/examples/states` | public | async and access state matrix |
|
|
| `EXAMPLES_AUTH` | `/examples/auth` | public | session integration controls |
|
|
| `SAMPLE_RESOURCE_LIST` | `/sample/resources` | integration-defined | protected integration seam |
|
|
| `NOT_FOUND` | `*` | public | safe navigation recovery |
|
|
|
|
Navigation labels and order come from `ROUTE_REGISTRY`; the sidebar does not
|
|
maintain a second route list. The client access decision never claims to be
|
|
authorization.
|
|
|
|
## Authentication seam
|
|
|
|
The session port exposes state subscription, sign-in start, sign-out,
|
|
credential attachment, recovery, and unauthenticated notification. Credentials
|
|
remain opaque to the application and presentation layers.
|
|
|
|
- `demo`: local/development-only state transition with no credentials
|
|
- `external`: delegates to `globalThis.__CA_FRONTEND_AUTH_OWNER__`
|
|
- missing/invalid external owner: fails closed as `integration-failed`
|
|
|
|
An external owner implements `readState`, `subscribe`, `beginSignIn`,
|
|
`signOut`, `attachCredential`, `recoverSession`, and
|
|
`notifyUnauthenticated`. It owns token acquisition and storage.
|
|
|
|
## Extending the starter
|
|
|
|
The steps below describe the current extension path. The platform review found
|
|
that several route metadata fields and the composed application facade are not
|
|
yet connected end to end. New platform work should follow
|
|
[routing, page templates, and reusable patterns](./routing-pages-and-patterns.md)
|
|
and the
|
|
[TypeScript, state, and data-flow target](./typescript-state-and-data-flow.md)
|
|
rather than adding another independent route or data-loading convention.
|
|
|
|
1. Register the route path, access hint, title, chunk, loading surface, error
|
|
surface, and optional navigation metadata in `src/contracts/routes.js`.
|
|
2. Add a lazy page in `src/presentation/` and render it through `RouteSurface`.
|
|
3. Use application ports or use cases; do not import concrete adapters.
|
|
4. Use the semantic tokens, UI primitives, and state surfaces before adding a
|
|
project-specific variant.
|
|
5. Add component behavior, all-engine E2E, automated axe, and signed manual
|
|
route evidence.
|
|
6. Run `test:sample-removal` to prove the visible starter still builds without
|
|
`src/sample/contract-fixture`.
|
|
|
|
Theme preference is the public `COLOR_SCHEME` storage contract. Authentication
|
|
tokens and other secrets remain forbidden storage keys.
|