begin; set local standard_conforming_strings = on; set local lock_timeout = '5s'; select pg_advisory_xact_lock(hashtextextended('proposal-rollback:' || E'edaf2c90-af15-5a2f-b6b9-fe08ab9ae81b', 0)); do $rollback$ declare affected integer; approval_now jsonb; downstream_dependency_count integer; begin perform 1 from kb_stage.kb_proposals where id = E'edaf2c90-af15-5a2f-b6b9-fe08ab9ae81b'::uuid for update; if not found then raise exception 'proposal rollback: proposal row missing'; end if; if not exists ( select 1 from kb_stage.kb_proposals where id = E'edaf2c90-af15-5a2f-b6b9-fe08ab9ae81b'::uuid and proposal_type = 'approve_claim' and status = 'applied' and payload = E'{"apply_payload":{"agent_id":null,"claims":[{"confidence":0.9,"created_by":null,"id":"b4d0a944-8f11-5516-80ca-bc680f0059ad","status":"open","superseded_by":null,"tags":["working-leo","clone-canary"],"text":"An approved strict proposal can create exact canonical rows atomically.","type":"structural"},{"confidence":0.85,"created_by":null,"id":"a9dd972a-b867-56f7-b3c9-3913dd9a0abe","status":"open","superseded_by":null,"tags":["working-leo","row-proof"],"text":"Row-level proof is the authority for canonical KB state.","type":"concept"}],"contract_version":2,"edges":[{"created_by":null,"edge_type":"supports","from_claim":"b4d0a944-8f11-5516-80ca-bc680f0059ad","to_claim":"a9dd972a-b867-56f7-b3c9-3913dd9a0abe","weight":0.75}],"evidence":[{"claim_id":"b4d0a944-8f11-5516-80ca-bc680f0059ad","created_by":null,"role":"grounds","source_id":"3953271f-7df5-5674-99b0-980b1b3534e6","weight":0.9},{"claim_id":"a9dd972a-b867-56f7-b3c9-3913dd9a0abe","created_by":null,"role":"illustrates","source_id":"3d31345d-a4f7-52a7-af4a-0034f99a8123","weight":0.8}],"reasoning_tools":[{"agent_id":null,"category":"verification","description":"Verify approved proposal to canonical graph lifecycle in a disposable clone.","id":"a32a7252-d39f-5ee9-873a-a82b56a6bb08","name":"Canonical row proof canary"}],"sources":[{"created_by":null,"excerpt":"Disposable clone lifecycle canary source A.","hash":"approve-claim-canary-e315c2518c-a","id":"3953271f-7df5-5674-99b0-980b1b3534e6","source_type":"observation","storage_path":null,"url":null},{"created_by":null,"excerpt":"Disposable clone lifecycle canary source B.","hash":"approve-claim-canary-e315c2518c-b","id":"3d31345d-a4f7-52a7-af4a-0034f99a8123","source_type":"observation","storage_path":null,"url":null}]}}'::jsonb and reviewed_by_handle is not distinct from E'm3ta' and reviewed_by_agent_id is not distinct from E'99999999-9999-9999-9999-999999999999'::uuid and reviewed_at is not distinct from E'2026-07-15 03:59:09.091704+00'::timestamptz and review_note is not distinct from E'Reviewed exact strict payload inside the disposable clone.' and applied_by_handle is not distinct from E'kb-apply' and applied_by_agent_id is not distinct from E'44444444-4444-4444-4444-444444444444'::uuid and applied_at is not distinct from E'2026-07-15 03:59:12.452878+00'::timestamptz ) then raise exception 'proposal rollback: applied ledger does not match apply receipt'; end if; select jsonb_build_object( 'proposal_id', proposal_id::text, 'proposal_type', proposal_type, 'payload', payload, 'reviewed_by_handle', reviewed_by_handle, 'reviewed_by_agent_id', reviewed_by_agent_id::text, 'reviewed_by_db_role', reviewed_by_db_role::text, 'reviewed_at', reviewed_at::text, 'review_note', review_note ) into approval_now from kb_stage.kb_proposal_approvals where proposal_id = E'edaf2c90-af15-5a2f-b6b9-fe08ab9ae81b'::uuid; if approval_now is distinct from E'{"payload":{"apply_payload":{"agent_id":null,"claims":[{"confidence":0.9,"created_by":null,"id":"b4d0a944-8f11-5516-80ca-bc680f0059ad","status":"open","superseded_by":null,"tags":["working-leo","clone-canary"],"text":"An approved strict proposal can create exact canonical rows atomically.","type":"structural"},{"confidence":0.85,"created_by":null,"id":"a9dd972a-b867-56f7-b3c9-3913dd9a0abe","status":"open","superseded_by":null,"tags":["working-leo","row-proof"],"text":"Row-level proof is the authority for canonical KB state.","type":"concept"}],"contract_version":2,"edges":[{"created_by":null,"edge_type":"supports","from_claim":"b4d0a944-8f11-5516-80ca-bc680f0059ad","to_claim":"a9dd972a-b867-56f7-b3c9-3913dd9a0abe","weight":0.75}],"evidence":[{"claim_id":"b4d0a944-8f11-5516-80ca-bc680f0059ad","created_by":null,"role":"grounds","source_id":"3953271f-7df5-5674-99b0-980b1b3534e6","weight":0.9},{"claim_id":"a9dd972a-b867-56f7-b3c9-3913dd9a0abe","created_by":null,"role":"illustrates","source_id":"3d31345d-a4f7-52a7-af4a-0034f99a8123","weight":0.8}],"reasoning_tools":[{"agent_id":null,"category":"verification","description":"Verify approved proposal to canonical graph lifecycle in a disposable clone.","id":"a32a7252-d39f-5ee9-873a-a82b56a6bb08","name":"Canonical row proof canary"}],"sources":[{"created_by":null,"excerpt":"Disposable clone lifecycle canary source A.","hash":"approve-claim-canary-e315c2518c-a","id":"3953271f-7df5-5674-99b0-980b1b3534e6","source_type":"observation","storage_path":null,"url":null},{"created_by":null,"excerpt":"Disposable clone lifecycle canary source B.","hash":"approve-claim-canary-e315c2518c-b","id":"3d31345d-a4f7-52a7-af4a-0034f99a8123","source_type":"observation","storage_path":null,"url":null}]}},"proposal_id":"edaf2c90-af15-5a2f-b6b9-fe08ab9ae81b","proposal_type":"approve_claim","review_note":"Reviewed exact strict payload inside the disposable clone.","reviewed_at":"2026-07-15 03:59:09.091704+00","reviewed_by_agent_id":"99999999-9999-9999-9999-999999999999","reviewed_by_db_role":"kb_review","reviewed_by_handle":"m3ta"}'::jsonb then raise exception 'proposal rollback: immutable approval snapshot drifted'; end if; select count(*) into downstream_dependency_count from ( select ce.claim_id from public.claim_evidence ce where (ce.claim_id = any(array[E'a9dd972a-b867-56f7-b3c9-3913dd9a0abe'::uuid, E'b4d0a944-8f11-5516-80ca-bc680f0059ad'::uuid]::uuid[]) or ce.source_id = any(array[E'3953271f-7df5-5674-99b0-980b1b3534e6'::uuid, E'3d31345d-a4f7-52a7-af4a-0034f99a8123'::uuid]::uuid[])) and not (((ce.claim_id = E'a9dd972a-b867-56f7-b3c9-3913dd9a0abe'::uuid and ce.source_id = E'3d31345d-a4f7-52a7-af4a-0034f99a8123'::uuid and ce.role = E'illustrates'::evidence_role) or (ce.claim_id = E'b4d0a944-8f11-5516-80ca-bc680f0059ad'::uuid and ce.source_id = E'3953271f-7df5-5674-99b0-980b1b3534e6'::uuid and ce.role = E'grounds'::evidence_role))) union all select edge.id from public.claim_edges edge where (edge.from_claim = any(array[E'a9dd972a-b867-56f7-b3c9-3913dd9a0abe'::uuid, E'b4d0a944-8f11-5516-80ca-bc680f0059ad'::uuid]::uuid[]) or edge.to_claim = any(array[E'a9dd972a-b867-56f7-b3c9-3913dd9a0abe'::uuid, E'b4d0a944-8f11-5516-80ca-bc680f0059ad'::uuid]::uuid[])) and edge.id <> all(array[E'cd799806-18e8-5e8c-959c-5f9c267654a7'::uuid]::uuid[]) union all select claim.id from public.claims claim where claim.superseded_by = any(array[E'a9dd972a-b867-56f7-b3c9-3913dd9a0abe'::uuid, E'b4d0a944-8f11-5516-80ca-bc680f0059ad'::uuid]::uuid[]) and claim.id <> all(array[E'a9dd972a-b867-56f7-b3c9-3913dd9a0abe'::uuid, E'b4d0a944-8f11-5516-80ca-bc680f0059ad'::uuid]::uuid[]) ) external_dependencies; if downstream_dependency_count <> 0 then raise exception 'proposal rollback: % downstream dependenc(ies) exist; rollback quarantined', downstream_dependency_count; end if; if (select count(*) from public.claim_evidence t where ((t.claim_id = E'a9dd972a-b867-56f7-b3c9-3913dd9a0abe'::uuid and t.source_id = E'3d31345d-a4f7-52a7-af4a-0034f99a8123'::uuid and t.role = E'illustrates'::evidence_role)) and to_jsonb(t) = E'{"claim_id":"a9dd972a-b867-56f7-b3c9-3913dd9a0abe","created_at":"2026-07-15T03:59:12.43629+00:00","created_by":null,"role":"illustrates","source_id":"3d31345d-a4f7-52a7-af4a-0034f99a8123","weight":0.8}'::jsonb) <> 1 then raise exception 'proposal rollback drift: claim_evidence[0] row does not match apply receipt'; end if; if (select count(*) from public.claim_evidence t where ((t.claim_id = E'b4d0a944-8f11-5516-80ca-bc680f0059ad'::uuid and t.source_id = E'3953271f-7df5-5674-99b0-980b1b3534e6'::uuid and t.role = E'grounds'::evidence_role)) and to_jsonb(t) = E'{"claim_id":"b4d0a944-8f11-5516-80ca-bc680f0059ad","created_at":"2026-07-15T03:59:12.43629+00:00","created_by":null,"role":"grounds","source_id":"3953271f-7df5-5674-99b0-980b1b3534e6","weight":0.9}'::jsonb) <> 1 then raise exception 'proposal rollback drift: claim_evidence[1] row does not match apply receipt'; end if; if (select count(*) from public.claim_edges t where t.id = E'cd799806-18e8-5e8c-959c-5f9c267654a7'::uuid and to_jsonb(t) = E'{"created_at":"2026-07-15T03:59:12.43629+00:00","created_by":null,"edge_type":"supports","from_claim":"b4d0a944-8f11-5516-80ca-bc680f0059ad","id":"cd799806-18e8-5e8c-959c-5f9c267654a7","to_claim":"a9dd972a-b867-56f7-b3c9-3913dd9a0abe","weight":0.75}'::jsonb) <> 1 then raise exception 'proposal rollback drift: claim_edges[0] row does not match apply receipt'; end if; if (select count(*) from public.reasoning_tools t where t.id = E'a32a7252-d39f-5ee9-873a-a82b56a6bb08'::uuid and to_jsonb(t) = E'{"agent_id":null,"category":"verification","created_at":"2026-07-15T03:59:12.43629+00:00","description":"Verify approved proposal to canonical graph lifecycle in a disposable clone.","id":"a32a7252-d39f-5ee9-873a-a82b56a6bb08","name":"Canonical row proof canary"}'::jsonb) <> 1 then raise exception 'proposal rollback drift: reasoning_tools[0] row does not match apply receipt'; end if; if (select count(*) from public.sources t where t.id = E'3953271f-7df5-5674-99b0-980b1b3534e6'::uuid and to_jsonb(t) = E'{"captured_at":null,"created_at":"2026-07-15T03:59:12.43629+00:00","created_by":null,"excerpt":"Disposable clone lifecycle canary source A.","hash":"approve-claim-canary-e315c2518c-a","id":"3953271f-7df5-5674-99b0-980b1b3534e6","source_type":"observation","storage_path":null,"url":null}'::jsonb) <> 1 then raise exception 'proposal rollback drift: sources[0] row does not match apply receipt'; end if; if (select count(*) from public.sources t where t.id = E'3d31345d-a4f7-52a7-af4a-0034f99a8123'::uuid and to_jsonb(t) = E'{"captured_at":null,"created_at":"2026-07-15T03:59:12.43629+00:00","created_by":null,"excerpt":"Disposable clone lifecycle canary source B.","hash":"approve-claim-canary-e315c2518c-b","id":"3d31345d-a4f7-52a7-af4a-0034f99a8123","source_type":"observation","storage_path":null,"url":null}'::jsonb) <> 1 then raise exception 'proposal rollback drift: sources[1] row does not match apply receipt'; end if; if (select count(*) from public.claims t where t.id = E'a9dd972a-b867-56f7-b3c9-3913dd9a0abe'::uuid and to_jsonb(t) = E'{"confidence":0.85,"created_at":"2026-07-15T03:59:12.43629+00:00","created_by":null,"id":"a9dd972a-b867-56f7-b3c9-3913dd9a0abe","status":"open","superseded_by":null,"tags":["working-leo","row-proof"],"text":"Row-level proof is the authority for canonical KB state.","type":"concept","updated_at":"2026-07-15T03:59:12.43629+00:00"}'::jsonb) <> 1 then raise exception 'proposal rollback drift: claims[0] row does not match apply receipt'; end if; if (select count(*) from public.claims t where t.id = E'b4d0a944-8f11-5516-80ca-bc680f0059ad'::uuid and to_jsonb(t) = E'{"confidence":0.9,"created_at":"2026-07-15T03:59:12.43629+00:00","created_by":null,"id":"b4d0a944-8f11-5516-80ca-bc680f0059ad","status":"open","superseded_by":null,"tags":["working-leo","clone-canary"],"text":"An approved strict proposal can create exact canonical rows atomically.","type":"structural","updated_at":"2026-07-15T03:59:12.43629+00:00"}'::jsonb) <> 1 then raise exception 'proposal rollback drift: claims[1] row does not match apply receipt'; end if; delete from public.claim_evidence target where ((target.claim_id = E'a9dd972a-b867-56f7-b3c9-3913dd9a0abe'::uuid and target.source_id = E'3d31345d-a4f7-52a7-af4a-0034f99a8123'::uuid and target.role = E'illustrates'::evidence_role) or (target.claim_id = E'b4d0a944-8f11-5516-80ca-bc680f0059ad'::uuid and target.source_id = E'3953271f-7df5-5674-99b0-980b1b3534e6'::uuid and target.role = E'grounds'::evidence_role)); get diagnostics affected = row_count; if affected <> 2 then raise exception 'proposal rollback count mismatch for claim_evidence: expected 2, got %', affected; end if; delete from public.claim_edges where id in (E'cd799806-18e8-5e8c-959c-5f9c267654a7'::uuid); get diagnostics affected = row_count; if affected <> 1 then raise exception 'proposal rollback count mismatch for claim_edges: expected 1, got %', affected; end if; delete from public.reasoning_tools where id in (E'a32a7252-d39f-5ee9-873a-a82b56a6bb08'::uuid); get diagnostics affected = row_count; if affected <> 1 then raise exception 'proposal rollback count mismatch for reasoning_tools: expected 1, got %', affected; end if; delete from public.sources where id in (E'3953271f-7df5-5674-99b0-980b1b3534e6'::uuid, E'3d31345d-a4f7-52a7-af4a-0034f99a8123'::uuid); get diagnostics affected = row_count; if affected <> 2 then raise exception 'proposal rollback count mismatch for sources: expected 2, got %', affected; end if; delete from public.claims where id in (E'a9dd972a-b867-56f7-b3c9-3913dd9a0abe'::uuid, E'b4d0a944-8f11-5516-80ca-bc680f0059ad'::uuid); get diagnostics affected = row_count; if affected <> 2 then raise exception 'proposal rollback count mismatch for claims: expected 2, got %', affected; end if; update kb_stage.kb_proposals set status = 'canceled', applied_by_handle = null, applied_by_agent_id = null, applied_at = null, updated_at = now() where id = E'edaf2c90-af15-5a2f-b6b9-fe08ab9ae81b'::uuid and status = 'applied' and payload = E'{"apply_payload":{"agent_id":null,"claims":[{"confidence":0.9,"created_by":null,"id":"b4d0a944-8f11-5516-80ca-bc680f0059ad","status":"open","superseded_by":null,"tags":["working-leo","clone-canary"],"text":"An approved strict proposal can create exact canonical rows atomically.","type":"structural"},{"confidence":0.85,"created_by":null,"id":"a9dd972a-b867-56f7-b3c9-3913dd9a0abe","status":"open","superseded_by":null,"tags":["working-leo","row-proof"],"text":"Row-level proof is the authority for canonical KB state.","type":"concept"}],"contract_version":2,"edges":[{"created_by":null,"edge_type":"supports","from_claim":"b4d0a944-8f11-5516-80ca-bc680f0059ad","to_claim":"a9dd972a-b867-56f7-b3c9-3913dd9a0abe","weight":0.75}],"evidence":[{"claim_id":"b4d0a944-8f11-5516-80ca-bc680f0059ad","created_by":null,"role":"grounds","source_id":"3953271f-7df5-5674-99b0-980b1b3534e6","weight":0.9},{"claim_id":"a9dd972a-b867-56f7-b3c9-3913dd9a0abe","created_by":null,"role":"illustrates","source_id":"3d31345d-a4f7-52a7-af4a-0034f99a8123","weight":0.8}],"reasoning_tools":[{"agent_id":null,"category":"verification","description":"Verify approved proposal to canonical graph lifecycle in a disposable clone.","id":"a32a7252-d39f-5ee9-873a-a82b56a6bb08","name":"Canonical row proof canary"}],"sources":[{"created_by":null,"excerpt":"Disposable clone lifecycle canary source A.","hash":"approve-claim-canary-e315c2518c-a","id":"3953271f-7df5-5674-99b0-980b1b3534e6","source_type":"observation","storage_path":null,"url":null},{"created_by":null,"excerpt":"Disposable clone lifecycle canary source B.","hash":"approve-claim-canary-e315c2518c-b","id":"3d31345d-a4f7-52a7-af4a-0034f99a8123","source_type":"observation","storage_path":null,"url":null}]}}'::jsonb and applied_at is not distinct from E'2026-07-15 03:59:12.452878+00'::timestamptz; get diagnostics affected = row_count; if affected <> 1 then raise exception 'proposal rollback: expected one applied ledger row, got %', affected; end if; end $rollback$; commit;