# V2 Phase C Implementation Evidence

**Revision:** `0.2.0` working tree  
**Date:** 26 August 2026  
**Policy/API/schema:** `sim-policy-2026-08-26.4` / `v2 phase-c` / `sim-schema-v2-phase-c`  
**Scope:** booking orchestration, exact fare consent, synthetic payment, fake-PRS outcome, ticket, My Trips, and PNR retrieval

## Implemented passenger journeys

- General selection creates a server-backed booking draft and proceeds without a queue.
- Tatkal and Premium Tatkal continue only from an admitted Phase B attempt and re-verify the session-bound permit before quote and commit.
- Five saved synthetic passenger fixtures start unselected. The UI accepts no free-form identity, contact, government-ID, bank, card, UPI, PIN, CVV, password, or OTP field.
- Exact fare review shows the selected journey and complete component sum. Affirmative consent is bound to passenger references, quote ID, minor-unit total, inventory version, pricing version, and expiry.
- Demo UPI, demo card, and demo net banking are presentation-only method choices. Outcome selection is server-side scenario data and is not in the public API request.
- Results distinguish confirmed, RAC, waitlist, declined, unknown/reconciling, sold-out, and refund-pending states. Only confirmed/RAC/waitlist create a synthetic PNR-like reference, and every ticket states that it is not valid for travel.
- `/trips` lists the current anonymous session’s outcomes. `/pnr` retrieves current-session references plus documented fixture `DMO260001`.

## Correctness and safety evidence

| Requirement | Evidence |
| --- | --- |
| General bypasses queue | `tests/phase-c.test.ts` creates and completes a General draft without a queue entry. |
| Protected permit enforced | Protected integration test advances the cohort, offers, claims, then quotes and commits; an unclaimed reference is rejected. |
| Exact fare consent | Binding test rejects a one-minor-unit mismatch with `PRICE_CHANGED`; schemas also require accepted inventory and pricing versions. |
| Replay is exactly once | Duplicate booking key returns the same booking reference and leaves one result/allocation. |
| Unknown blocks retry | Original idempotency replay succeeds; a different booking key receives `PAYMENT_UNKNOWN`. |
| Segment allocation | Two sessions booking the same segment receive different berths; the atomic store prevents overlapping berth/segment effects. |
| PT confirmed-only | Phase C commit maps RAC/waitlist only from General catalogue states and increments PT sold units only after confirmed allocation. |
| Retrieval isolation | Trips and generated PNRs are invisible to another anonymous session; the public fixture remains explicitly synthetic. |
| Sensitive-data boundary | Strict Zod request objects accept fixture refs and mock method enums only; unexpected fields are rejected and none are logged. |

## Local verification

```text
pnpm typecheck  PASS
pnpm test       PASS — 5 files, 43 tests
```

```text
pnpm build       PASS — Next.js 16.3.2 production build; all Phase C routes emitted
Browser smoke    PASS — General search → passenger → quote/consent → Demo UPI → confirmed ticket → My Trips → PNR
Mobile smoke     PASS — 390 × 844 PNR/retrieval page, no horizontal document overflow
Console errors   0 during the production-build browser journey
```

## Remaining evidence owned by Phase D or deployment

- Automated browser coverage for the full timing-dependent Tatkal journey, keyboard-only operation, screen-reader announcements, 200%/400% reflow, reduced motion, offline recovery, and slow-network behavior.
- Public-link Redis restart and multi-process idempotency smoke using deployment credentials.
- Reconciliation worker for an `UNKNOWN` payment; Phase C safely blocks retry and makes no convergence claim.
- Production-shaped PostgreSQL adapter. The local/Redis-compatible atomic state adapter persists Phase C state; SQL tables document the durable relational target.
