# S06: Live environment stabilization and integrated acceptance rerun — UAT **Milestone:** M001 **Written:** 2026-03-27T08:29:02.335Z # S06 UAT — Live environment stabilization and integrated acceptance rerun ## Goal Prove that the real localhost environment can be started, preflighted, seeded with acceptance-ready data, and used to rerun the integrated daily loop for the deterministic acceptance fixture without crossing the manual-send boundary. The concrete fixture for this slice is: - Company: `S06 Acceptance Labs` - Job: `S06 Acceptance Backend Engineer` - Expected workflow state: `Follow up`, `Ready`, `Waiting 14d` ## Preconditions 1. Backend is running at `http://localhost:5202` and frontend is running at `http://localhost:3000`. 2. The worktree contains the S06 scripts and `docs/s06-acceptance-run.md`. 3. If running the seed script directly, a valid bearer token is available in `AUTH_TOKEN`. 4. If running only `bash scripts/s06-acceptance-run.sh`, the default localhost dev JWT fallback is allowed to mint a local token from the checked-in dev JWT settings plus the local SQLite admin user. 5. Do **not** click `Send And Log Email` unless outbound mail is intentionally pointed at a safe sink. --- ## Test Case 1 — Preflight catches the real environment state before browser work ### Steps 1. Run `bash scripts/s06-preflight.sh`. 2. Review the printed readiness lines. ### Expected - The script prints `Preflight target: http://localhost:5202/api`. - The script prints the required origin pair `UI http://localhost:3000 -> API http://localhost:5202/api`. - The script reports `auth.requireAuth=true` and the auth config surface is reachable. - If `/api/admin/system` is not called with an admin token, the script still exits successfully with the guided partial-pass message instead of failing ambiguously. ### Edge checks - If the API is down or `API_BASE` is wrong, the script exits non-zero with a clear start-the-API hint. - If the API returns malformed JSON, the script prints the raw body and fails. --- ## Test Case 2 — Acceptance seeding produces the deterministic live fixture ### Steps 1. Export a valid token to `AUTH_TOKEN`. 2. Run `bash scripts/s06-acceptance-data.sh`. 3. Review the seed summary output. 4. Run the script a second time. ### Expected - The script prints `seed.result=success`. - The script prints stable `seed.company.id` / `seed.job.id` values and does not create duplicate jobs on rerun. - The script prints `seed.workflow.action=follow-up`. - The script prints `seed.readiness.level=Ready`. - The script prints `seed.reminders=Waiting 14d`. - The job has saved Tailored CV / package state and recruiter-thread correspondence prepared for later browser verification. ### Edge checks - Running without `AUTH_TOKEN` fails immediately with guidance. - Running with a bad token fails clearly as an auth issue. - Re-running the seed does not create duplicate deterministic correspondence for the same external message id. --- ## Test Case 3 — The acceptance runner refreshes the artifact and keeps evidence on disk ### Steps 1. Run `bash scripts/s06-acceptance-run.sh`. 2. Confirm `docs/s06-acceptance-run.md` exists and is non-empty. 3. Open the generated markdown and review the shell summary table. ### Expected - The runner reports `acceptance.result=pass`. - The runner records `Preflight`, `Seed acceptance data`, and `UI trust-loop test` as pass states. - The markdown contains a current run id, timestamp, auth-token-source category, and log paths under `docs/artifacts/s06-acceptance/logs/`. - The guided browser section remains present after rerun and is not overwritten by the shell refresh. ### Edge checks - If preflight fails because the backend is unreachable, the runner exits non-zero and records the failure instead of proceeding. - If Gmail is not configured, the document calls that out as a live limitation rather than pretending Gmail continuity was proven. --- ## Test Case 4 — `/jobs` opens the seeded workspace with saved package state ### Steps 1. Open `http://localhost:3000/jobs` in the live app. 2. Locate the row for `S06 Acceptance Labs • S06 Acceptance Backend Engineer`. 3. Confirm the row shows `Follow up`, `CV ready`, and `Waiting` style signals. 4. Open the job workspace from that row. 5. Go to **Tailored CV**. ### Expected - The workspace opens for the seeded job, not a different row. - The Tailored CV area contains the saved seeded text beginning `Saved acceptance tailored CV highlighting ASP.NET Core delivery...`. - The saved package state is visible in the real workspace rather than only in test data or logs. ### Edge checks - Re-opening the same job should show the same saved package state; it should not disappear or duplicate on revisit. --- ## Test Case 5 — Follow-up drafting stays manual and does not auto-send ### Steps 1. From the same seeded job workspace, open **Follow up**. 2. Wait for the draft to load or regenerate it if needed. 3. Review the available actions. 4. Inspect the network log if available. 5. Stop **before** clicking `Send And Log Email`. ### Expected - The follow-up draft loads successfully from the live backend. - The UI shows separate `Copy Draft` and `Send And Log Email` actions. - Draft loading/regeneration calls `GET /api/jobapplications/{id}/followup-draft`. - No `POST /api/jobapplications/{id}/send-followup` request occurs during draft review/regeneration alone. - The manual-send boundary remains explicit and intact. ### Edge checks - Editing or regenerating the draft should not add a sent item to correspondence by itself. - If recruiter contact data is incomplete, drafting may still work while send remains the explicit guarded action. --- ## Test Case 6 — `/reminders` and `/dashboard` reflect the same seeded job coherently ### Steps 1. Open `http://localhost:3000/reminders`. 2. Find the seeded job under the follow-up grouping. 3. Confirm the job shows `Follow up`, `Waiting 14d`, and `Follow-up: 10/03/2026`. 4. Open `http://localhost:3000/dashboard`. 5. Confirm the dashboard analytics include the seeded job/company state. 6. Reload `/dashboard` and review browser diagnostics. ### Expected - `/reminders` shows the same seeded job that was opened from `/jobs`. - `/dashboard` includes `S06 Acceptance Labs` in the activity/company view. - The dashboard reload completes without console errors or failed network requests. - The app behaves as one coherent single-user loop across all three surfaces. ### Edge checks - If the job is missing from `/reminders`, the seed dates may no longer be beyond the active follow-up threshold and should be rechecked. - If `/dashboard` loads but records failed requests, treat the slice as not stabilized. --- ## Test Case 7 — Gmail continuity status is reported honestly ### Steps 1. In the seeded job workspace, open **Correspondence**. 2. Confirm the deterministic recruiter-thread message is present. 3. Check whether the workspace exposes connected Gmail state and whether any linked-thread refresh request runs. 4. Compare the observation with `docs/s06-acceptance-run.md`. ### Expected - The recruiter-thread message seeded by S06 is visible. - If Gmail is connected in the environment, a linked-thread refresh can be observed and reported. - If Gmail is **not** connected, the acceptance artifact explicitly records that Gmail continuity was not proven live in this run. ### Edge checks - Do not claim success for Gmail continuity merely because seeded correspondence is present. - Absence of `POST /api/gmail/refresh-linked-threads` in the live run means the slice only proved seeded correspondence visibility, not live Gmail refresh. --- ## Pass Criteria S06 passes when all of the following are true: - The localhost stack is startable on the expected UI/API origins. - Preflight provides a readable go/no-go result instead of failing with opaque CORS/runtime symptoms. - The deterministic acceptance fixture can be seeded repeatably without duplicate drift. - The seeded job appears coherently across `/jobs`, the workspace, `/reminders`, and `/dashboard`. - Follow-up drafting remains manual and does not auto-send. - `docs/s06-acceptance-run.md` contains current shell evidence and honest browser observations, including any remaining Gmail continuity limitation. ## Failure Clues - `scripts/s06-preflight.sh` fails because the API is unreachable or returns malformed JSON. - Seeding creates duplicate fixture data or no longer lands in `follow-up` / `Waiting 14d` state. - `/jobs`, workspace, `/reminders`, and `/dashboard` disagree about the seeded job’s next action. - Opening or regenerating a follow-up draft triggers a send request. - The acceptance artifact hides Gmail configuration limitations instead of recording them. - Dashboard reload still produces console errors or failed requests.