Skip to content
Merged
1 change: 1 addition & 0 deletions docs/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -100,6 +100,7 @@ npm run docs:check-links
- [search-rag-master-plan.md](search-rag-master-plan.md) / [search-rag-master-context.md](search-rag-master-context.md) — search/RAG roadmap and shared context
- [rag-improvement/README.md](rag-improvement/README.md) — reviewed/updated RAG improvement programme: answer-quality track (intent-aware related information, length) + corrected eval/safety infra track
- [rag-improvement/HANDOVER.md](rag-improvement/HANDOVER.md) — multi-session handover: per-session work packets, status table, checklists, and paste-ready prompts for executing the programme
- [rag-improvement/COORDINATION.md](rag-improvement/COORDINATION.md) — coordinator handover: programme history, wave/session decisions, babysit playbook, approvals map, and the coordination-chat bootstrap prompt
- [rag-hybrid-findings-and-todo.md](rag-hybrid-findings-and-todo.md) — hybrid retrieval findings backlog
- [reindex-shadow-harness-design.md](reindex-shadow-harness-design.md) — designed-only shadow reindex harness (driver not built)
- [ingestion-concurrency-fix-workorder.md](ingestion-concurrency-fix-workorder.md) — ingestion concurrency workorder
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
| 2026-08-17 | claude/rag-plan-review-guide-vhrls9 | 0171669b37f4c9c7fb72a7a931b8b326d4eb72a1 | docs/rag-improvement coordination handover + HANDOVER status sync + hazard H5a note + 6 inbox requests (PR #2024, post-#2022/#2023 merge) | docs-only; conflict with merged S1 row resolved; state re-verified against origin/main 2bd146eed and canary runs 31964560921 -> 32025082010 | prettier on touched docs; verify:pr-local docs scope (see PR body) |
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
| 2026-08-17 | claude/rag-plan-review-guide-vhrls9 | 704f8aebe0ca9df115b3b2b87fea735c847c8e88 | docs: coordination-chat handover (COORDINATION.md, HANDOVER status corrections, catalogue) | clean | verify:pr-local docs-focused scope green (format, docs gates, ledger checks) |
16 changes: 16 additions & 0 deletions docs/clinical-hazard-analysis.md
Original file line number Diff line number Diff line change
Expand Up @@ -117,6 +117,22 @@ _Pathway: coverage/confidence/trust gating. Note: the **coverage gate** (`evalua
| **H5d** | Hardcoded clozapine / patient-property branches in the coverage gate use looser accept criteria than the generic path ([`rag.ts:3726`](../src/lib/rag/rag.ts)) — inconsistent strictness per drug. | Low–Medium | Medium | downstream gates apply uniformly | none asserts cross-drug parity | Per-drug literals in a safety-adjacent gate. |
| **H5e** | Out-of-order response painting the wrong answer under a new question — **controlled**: a monotonic `searchRequestSeqRef` guards every state write incl. streamed progress ([`ClinicalDashboard.tsx`](../src/components/ClinicalDashboard.tsx), audit M10). | High (if it regressed) | Low | request-id guard | none (client React logic) | Minor: superseded stream has no `AbortController` (resource hygiene only). |

**H5a update (2026-08-17, coordinator review):** the fast-path half of H5a is now partially
mitigated — `deriveConfidence` (`src/lib/rag/rag-answer-support.ts`) computes
`strongestNonSynthetic` by excluding rows tagged `similarity_origin: "synthetic_text"` and
gates `"high"` on that value, so title-match synthetic scores no longer reach "high" on their
own. The **live residual** is a different, untagged path: `buildDocumentSummaryResults`
(`src/lib/rag/rag-row-contracts.ts`) stamps `similarity: 1` on document-summary rows with no
origin tag; its only caller is the document-summary route in `rag.ts`, never the general
answer path. **Owner decision 2026-08-17 — Option B:** add a distinct provenance value
(`"document_context"`) to the `similarity_origin` union and stamp it on those rows, keep the
confidence derivation unchanged (on the summary route the "query" is the document itself and
citation support is still verified by the same pipeline), pin the behaviour with tests, and
keep telemetry's `synthetic_similarity_count` from counting it. Option A (tag as
`synthetic_text` so summaries cap at "medium") was considered and rejected as a label
downgrade without a measured safety gain. Implementation packet: `docs/rag-improvement/HANDOVER.md`
§G1 (no retrieval behaviour change; no canary).

### H6 — Adversarial / corrupted document content changes the answer

_Pathway: uploaded document text → model context → answer. Detailed in the companion threat model; summarized here as a hazard._
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
{
"version": 2,
"id": "0649db55-c4ea-4683-b51c-4c6679754f81",
"createdOn": "2026-08-17",
"action": "add",
"payload": {
"pri": "P2",
"type": "task",
"summary": "R2 + R3: claim-support strictness rejects verbatim-faithful guideline restatements (directive normativity; topic-overlap dilution) — packet S1c",
"detail": "R2: normativeDirectiveActions in src/lib/rag/rag-claim-support.ts has no pattern for 'usual / recommended ... dose is ...' guideline phrasing, so imperative claims ('start lithium at 500 mg nocte') fail against descriptive norms; reproduced offline on the EMHS lithium chunk. R3: a claim synthesising two adjacent source bullets fails the >=50% single-segment topic-overlap requirement even when every atom matches; reproduced offline. Fix R2 with a small pattern addition plus adversarial negatives; MEASURE R3 before loosening. One PR after S1b merges and its canary is green; RAG impact behaviour change; canary pair. Packet: docs/rag-improvement/HANDOVER.md S1c. Stop: no grounding-gate weakening beyond the two named artefacts.",
"source": "RAG programme coordinator, S1 PR #2022 residuals and #212 handover follow-ups, 2026-08-17",
"issueUlid": "01M07SS71R6BG9X2VAGXMM1A1G"
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
{
"version": 2,
"id": "64dd6966-0697-4b70-a7ee-c8d526729404",
"createdOn": "2026-08-17",
"action": "add",
"payload": {
"pri": "P3",
"type": "task",
"summary": "Governance Option B decided: tag document-summary rows with similarity_origin 'document_context', keep the confidence label — implement as packet G1",
"detail": "Owner decision 2026-08-17 on the question queued by #212 tranche 3 (buildDocumentSummaryResults stamps similarity: 1 with no similarity_origin; deriveConfidence excludes only synthetic_text). Option B: add a new similarity_origin value document_context to the union in src/lib/types.ts and to src/lib/answer-stream-contract.ts, stamp it in buildDocumentSummaryResults (src/lib/rag/rag-row-contracts.ts), keep deriveConfidence unchanged and pin it with discriminating tests, keep rag.ts synthetic_similarity_count from counting it, and update docs/clinical-hazard-analysis.md H5a. Rationale: the only caller is the document-summary route where the query is the document itself and citation support is still verified; Option A (tag as synthetic_text so summaries cap at medium) rejected as a label downgrade without a measured safety gain. RAG impact: no retrieval behaviour change; no canary. Packet: docs/rag-improvement/HANDOVER.md G1. Closes the P1 governance question row once landed.",
"source": "RAG programme coordinator, S1 PR #2022 residuals and #212 handover follow-ups, 2026-08-17",
"issueUlid": "01M07SS7GT0MSNT8C71GX4KF5V"
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
{
"version": 2,
"id": "6c0d5004-45a4-42c8-b001-92428f76a0b0",
"createdOn": "2026-08-17",
"action": "add",
"payload": {
"pri": "P1",
"type": "task",
"summary": "R1: unbudgeted strong escalation makes provider_timeout the dominant lithium fallback — route the dosing class to strong before the deadline (packet S1b)",
"detail": "S1 (PR #2022) post-fix live probes: 'Lithium dosing?' 4/4 source-only, 3/4 as provider_timeout. fast_unsupported_retry_strong launches a strong generation into the fast route's leftover ~10-13 s; only the truncation self-heal is deadlineAllowsGenerationRetry-gated. Ladder rung 3 (README A1): route medication_dose_risk / dosing to the strong route in chooseAnswerRoute (src/lib/rag/rag-routing.ts) BEFORE the route deadline is created — not in shouldRetryWithStrongAfterFast, and NOT a budget change (#231 stop condition stands). Own PR, RAG impact behaviour change, canary pair, Clinical Governance Preflight, check:production-readiness. Owner decided 2026-08-17 this lands before S2 (A2/A3 add length; length under the unbudgeted retry pushes more dosing queries into timeout). Packet: docs/rag-improvement/HANDOVER.md S1b.",
"source": "RAG programme coordinator, S1 PR #2022 residuals and #212 handover follow-ups, 2026-08-17",
"issueUlid": "01M07SS6Y4DP6M3GKV5EFQXYPF"
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
{
"version": 2,
"id": "a3ba2812-2984-4fad-b959-6dfe69fb6aa8",
"createdOn": "2026-08-17",
"action": "add",
"payload": {
"pri": "P2",
"type": "issue",
"summary": "Recurring 'Unhandled server request error' on /api/search and /api/search/universal in Sentry — unowned, pre-dates #1946",
"detail": "Sentry (clinibase-xz): three issue groups in 24h, 17 events, 0 users impacted, on /api/search and /api/search/universal, all with culprit chunk 1261.js:2:4801. First seen 2026-08-14T08:44:37Z on release c9b089c9, about six hours before PR #1946 merged, so not caused by the row contracts. Recorded in the #212 tranche-1 handover; never captured durably until now. Next: triage the Sentry groups (read-only Sentry MCP or dashboard), map chunk 1261.js to source via the release's source maps, reproduce locally with the request shapes Sentry recorded. Stop: do not silence the error path; search routes are clinical output.",
"source": "RAG programme coordinator, S1 PR #2022 residuals and #212 handover follow-ups, 2026-08-17",
"issueUlid": "01M07SS758BTVMVKSAMK68GMS5"
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
{
"version": 2,
"id": "c156f1c0-8d83-460a-b1b5-ba970d664405",
"createdOn": "2026-08-17",
"action": "add",
"payload": {
"pri": "P3",
"type": "rec",
"summary": "eval-canary.yml is post-merge only (repository_dispatch + Sunday cron, no ref input) — record this in docs/rag-behaviour so sessions stop expecting a branch canary",
"detail": ".github/workflows/eval-canary.yml triggers on repository_dispatch type eval-canary and schedule cron 0 18 * * 0; it always loads the default branch and has no workflow_dispatch or ref input, so a canary can only ever measure main. Consequence for the RAG programme: 'canary pair' means latest green run on main before the merge -> a dispatch after the merge (gh api repos/BigSimmo/Database/dispatches -f event_type=eval-canary), compared with npm run eval:retrieval:compare -- <baseline.json> <post.json> --fail-on-regression on the eval-canary-output artifacts. Recorded correctly for S1 (baseline run 31964560921 -> post run 32025082010, zero regressions). Next: add one paragraph to docs/rag-behaviour/safeguards.md canary protocol; no workflow change.",
"source": "RAG programme coordinator, S1 PR #2022 residuals and #212 handover follow-ups, 2026-08-17",
"issueUlid": "01M07SS7D3TYJ0XPNKTBCWS5KV"
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
{
"version": 2,
"id": "ff73ce15-6890-44a1-8ddb-2919306a0e86",
"createdOn": "2026-08-17",
"action": "add",
"payload": {
"pri": "P3",
"type": "rec",
"summary": "source_metadata pin in rag-row-contracts.ts is data-backed only — add check (jsonb_typeof(metadata) = 'object') on documents or loosen the pin",
"detail": "src/lib/rag/rag-row-contracts.ts requires source_metadata to be a JSON object (z.record) while documents.metadata jsonb permits arrays and scalars. Live query 2026-08-14 (project sjrfecxgysukkwxsowpy): select jsonb_typeof(metadata), count(*) from public.documents group by 1 returned a single row, object = 2851, so nothing breaks today — but the guarantee is data, not schema, and a future ingest could make retrieval throw RetrievalRowShapeError for that document. Options: a check constraint via a new migration (role postgres; run check:migration-role) or loosen the pin. The module's doc comment also claims every required field is 'not null in supabase/schema.sql', which is true for nine fields and false for source_metadata — one-clause docs fix in the same PR.",
"source": "RAG programme coordinator, S1 PR #2022 residuals and #212 handover follow-ups, 2026-08-17",
"issueUlid": "01M07SS78VND10QT3784W1137Y"
}
}
Loading
Loading