Phase B Prerequisite 1 — Verification (data inventory + ontology pipeline)
Phase B Prerequisite 1 — Verification (data inventory + ontology pipeline)
Section titled “Phase B Prerequisite 1 — Verification (data inventory + ontology pipeline)”Date: 13/05/2026 (S234 end-of-session adversarial cross-check)
Audit purpose: Confirm accuracy of phase-b-prerequisite-1-data-inventory-RAW.md (1206 lines, ~145 entities) and phase-b-prerequisite-1-onthology-pipeline.md (542 lines, 6-layer retrospective mapping) before propagation into 0.9-decision-graph.md / 0.9-collapse-candidates.md / 00-synthesis-v2.md.
Verification baseline:
- Live DB introspection against
rovrymhhffssilaftdwd(production) —mcp__supabase__list_tables,mcp__supabase__execute_sqldescribing CHECK constraints, FK directions, UNIQUE / index shapes, generated columns, triggers, and distinct in-use enum values. - Filesystem inspection of
lib/,types/,app/api/cron/,mcp-apps/to verify code-domain claims. - Cross-reference against
0.9-context.md§7 (Phase B baseline anchors),0.9-intended-architecture.md§1.2 + §2 (planned shape), andfeedback-findings-review.md§5 (post-prereq dispositions — the canonical disposition register).
Audit scope decisions:
- Sampled 10 enum-shape CHECK constraints (out of ~40); verified all 30 row-counts cited in inventory § 1 (every count claim) against live DB.
- Sampled ~12 column-list claims for accuracy (content_items, content_history, content_chunks, content_citations, bid_questions, bid_responses, bid_response_history, source_documents, source_document_diffs, workspaces, classification_disputes, template_fields, template_requirements, templates, feed_articles, feed_flags, feed_sources, si_processing_queue, entity_mentions, entity_aliases, company_profiles, digests, pipeline_runs, processing_queue, notifications, tag_morphology_drift_flags, user_notification_prefs, verification_history, taxonomy_domains, taxonomy_subtopics, ingestion_quality_log).
- Verified all 46 public tables + 1 view; cross-checked the inventory’s enumeration is complete.
- Lifecycle-stage spot-checks against
0.9-intended-architecture.md§1.2 andfeedback-findings-review.md§5.
§1 — Inventory accuracy findings
Section titled “§1 — Inventory accuracy findings”1.1 Confirmed correct (high-volume sample, verbatim against live DB)
Section titled “1.1 Confirmed correct (high-volume sample, verbatim against live DB)”| Inventory claim | Verification source |
|---|---|
content_items 629 rows (line 65) | Live SQL count: 629 ✓ |
content_history 1223 rows (line 101) | Live SQL count: 1223 ✓ |
content_chunks 924 rows (line 109) | Live SQL count: 924 ✓ |
content_item_workspaces 81 rows (line 245) | Live SQL count: 81 ✓ |
template_requirements 96 rows (line 442) | Live SQL count: 96 ✓ |
feed_articles 410 rows (line 370) | Live SQL count: 410 ✓ |
feed_sources 26 rows (line 357) | Live SQL count: 26 ✓ |
feed_prompts 4 rows (line 363) | Live SQL count: 4 ✓ |
feed_flags 2 rows (line 382) | Live SQL count: 2 ✓ |
si_processing_queue 2144 rows (line 389) | Live SQL count: 2144 ✓ |
entity_mentions 1358 rows (line 623) | Live SQL count: 1358 ✓ |
entity_relationships 593 rows (line 631) | Live SQL count: 593 ✓ |
entity_aliases 24 rows (line 638) | Live SQL count: 24 ✓ |
notifications 592 rows (line 518) | Live SQL count: 592 ✓ |
digests 2 rows (line 532) | Live SQL count: 2 ✓ |
guides 11 rows (line 569) | Live SQL count: 11 ✓ |
guide_sections 135 rows (line 577) | Live SQL count: 135 ✓ |
taxonomy_domains 15 rows (line 584) | Live SQL count: 15 ✓ |
taxonomy_subtopics 57 rows (line 591) | Live SQL count: 57 ✓ |
layer_vocabulary 4 rows (line 605) | Live SQL count: 4 ✓ |
pipeline_runs 36 rows (line 709) | Live SQL count: 36 ✓ |
workspaces 4 rows all type='intelligence' (line 227-228) | Live SQL: 4 / all intelligence ✓ |
tag_morphology_drift_flags 3 rows (line 612) | Live SQL count: 3 ✓ |
read_marks 8 rows (line 125) | Live SQL count: 8 ✓ |
user_roles 9, user_profiles 9, company_profiles 1, source_documents 0, taxonomy_sync_state 1 | Live SQL all confirmed ✓ |
BID_STATES tuple = 10 values [draft, questions_extracted, matching, drafting, in_review, ready_for_export, submitted, won, lost, withdrawn] (line 269) | types/bid.ts:3-14 verbatim match ✓ |
lib/bid-library-ingest/ contains docx-to-markdown.ts, extract-answer.ts, extract-qa-pairs.ts, resolve-question.ts (line 207) | Filesystem ls confirms 4 files ✓ |
lib/quality/qa-detection.ts exists with patterns (line 204) | Filesystem confirms ✓ |
9 cron jobs at app/api/cron/* (line 733) | Filesystem confirms 9 dirs ✓ |
4 MCP Apps at mcp-apps/ (line 829) | Filesystem confirms bid-dashboard / coverage-matrix / intelligence-feed / reorient-me ✓ |
Lib subdirs ai/, bid/, mcp/, content/, coverage/, digest/, entities/, extraction/, quality/, source-documents/, supabase/, taxonomy/, templates/, validation/, intelligence/, ingest/, queue/, governance/, supersession/ (line 11) | Filesystem all present ✓ |
content_text_hash GENERATED ALWAYS expression on content_items (line 77) | information_schema.columns.is_generated='ALWAYS'; expression is md5(trim(regexp_replace(regexp_replace(lower(trim(content)), '[^\\w\\s]', '', 'g'), '\\s+', ' ', 'g'))) ✓ |
feed_articles.external_url UNIQUE per workspace (line 372) | idx_feed_articles_dedup UNIQUE INDEX on (workspace_id, external_url) ✓ |
entity_mentions UNIQUE (canonical_name, entity_type, content_item_id) (line 626) | Live constraint confirms ✓ |
entity_aliases.category ∈ {client, generic} (line 640) | Live distinct query confirms ✓ |
content_type enum 15 values (line 69) | CHECK definition is 15 values verbatim ✓ |
platform enum 6 values (line 69) | CHECK definition is 6 values verbatim ✓ |
dedup_status 5 values (line 77) | CHECK confirms ✓ |
publication_status 4 values (line 75) | CHECK confirms ✓ |
governance_review_status 5 values (line 75) | CHECK confirms ✓ |
entity_type 12 values on entity_mentions (line 625) | CHECK confirms ✓ |
relationship_type 10 values on entity_relationships (line 633) | CHECK confirms ✓ |
notifications.type 15 values + entity_type 6 values (line 520) | CHECK confirms both ✓ |
46 public tables + 1 view (quality_issues_pending line 949) | Live pg_tables query confirms ✓ |
1.2 Inaccuracies found
Section titled “1.2 Inaccuracies found”| Inventory claim | Actual state | Severity | Fix recommendation |
|---|---|---|---|
Line 171: q_a_pair content_items “~387 rows historically” | Live count: 395 | LOW | Update to 395; doesn’t change material conclusions but propagates to ontology doc §4.4. |
Line 103-104: content_history.change_type is “(edit/classify/import/archive/delete) (5 in use)“ | Actual CHECK lists 11 values: create, edit, ai_update, import, merge, rollback, archive, delete, metadata_change, owner_change, publication_state. Actual in-use values are 5 but different from inventory’s claim: archive, create, edit, metadata_change, owner_change. Inventory’s “classify / import / delete” are NOT in-use; create / metadata_change / owner_change are missing from inventory. | HIGH | Rewrite: enum has 11 valid values; 5 in use = archive, create, edit, metadata_change, owner_change. Propagates to ontology §2.1 (CV row 11) which carried the wrong 5 values forward. |
Line 443: template_requirements.requirement_type enum = (declaration/evidence/checklist) | Actual CHECK: 7 values = policy, statement, evidence, data, narrative, declaration, reference. checklist is NOT in the actual enum. | CRITICAL | Rewrite line 443. Cascades to ontology doc §2.1 row 12 (“(current values TBD)”) and §5 row “Form requirement_type='checklist' ENUM addition — RESOLVED-DIRECTIONAL — NO” — the ontology disposition is still correct (don’t add checklist), but its justification (“Checklist is a form_FORMAT not a requirement_TYPE”) is built on the FALSE premise that the inventory had checklist as an existing value. The actual decision is “no NEW value checklist is needed; the existing 7-value taxonomy suffices.” |
Line 443: template_type claims “(PQQ/ITT/etc.)” | Actual CHECK: 10 values = sq, rfp, eqq, pqq, gcloud, method_statement, dos, dps, framework, other. ITT is NOT in the actual enum. | HIGH | Rewrite to enumerate the 10 actual values. Inventory’s Charnwood “ITT 30 rows” claim (line 441) refers to source documents categorised under SOMETHING in template_type, not literally template_type='ITT'. |
Line 429: template_fields.field_type enum = (placeholder/table_cell) | Actual CHECK: 3 values = empty_cell, placeholder, highlighted. table_cell is NOT in actual enum. | HIGH | Rewrite to (empty_cell, placeholder, highlighted). |
Line 429: template_fields.mapping_status = (unmapped/auto_mapped/confirmed/rejected) | Actual CHECK: 5 values = unreviewed, confirmed, rejected, manual, unmapped. auto_mapped is NOT present; unreviewed and manual are missing from inventory. | HIGH | Rewrite. |
Line 280: bid_questions.status = (not_started/ai_drafted/in_progress/needs_review/complete) | Actual CHECK: 7 values = pending, in_progress, drafted, reviewed, final, skipped, complete. not_started, ai_drafted, needs_review are NOT in actual enum; pending, drafted, reviewed, final, skipped are missing from inventory. | HIGH | Rewrite to enumerate the 7 actual values. |
Line 229: workspaces.status = “(workflow state: draft/active/won/lost/etc.)” | Actual CHECK: the 10 BID_STATES verbatim. No value active exists — it was replaced by questions_extracted in the BID_STATES migration. | MEDIUM | Replace with the 10-value list. The “draft / active / won / lost / etc.” framing misleads downstream readers into thinking workspaces have a generic workflow rather than a bid-specific one. |
Line 391: si_processing_queue.status enum (unstated) | Actual CHECK: pending, processing, complete, failed. Inventory mentions the column but doesn’t enumerate; should be explicit. | LOW | Add the 4-value list. |
Line 571: guides.guide_type = “(sector / product / company / research / custom / completeness)“ | Actual CHECK: 5 values = sector, product, company, research, custom. completeness is NOT in actual enum. | MEDIUM | Remove completeness from inventory’s claim. (Cross-check: 0.9-context.md and feedback don’t claim completeness exists either; it’s an inventory fabrication.) |
Line 350: company_profiles.slug (UNIQUE) | No UNIQUE constraint or unique index on company_profiles.slug. Only name would be eligible, but no UNIQUE constraint exists. | MEDIUM | Drop the “(UNIQUE)” annotation OR add a migration to create the unique index if intended. |
Line 350: company_profiles column list | Inventory omits: is_active, is_primary, company_embedding (vector). | MEDIUM | Add these three columns to the entity’s key-attributes list. |
Line 534: digests columns claim filters (jsonb), governance_summary (jsonb) | Neither column exists in actual schema. Actual extra column is metadata (jsonb). | HIGH | Replace filters + governance_summary with metadata. Cascades to ontology doc §2.2 administrative-metadata claim (line 121) which inherited the inventory’s column list. |
Line 372: feed_articles column list | Inventory omits: extraction_method (with its 5-value CHECK enum: rss_content / fetch / jina_reader / firecrawl / summary_fallback), created_at, updated_at. | MEDIUM | Add extraction_method (with its CHECK enum) as another Layer-1 CV in ontology §2.1; add the timestamps. |
Line 411: source_document_diffs.diff_type (added/removed/modified/unchanged) | Actual CHECK: matches. But inventory omits diff_mode column (CHECK qa, full_text). | MEDIUM | Add diff_mode to inventory. Cascades to ontology §2.1 (additional CV row) or §2.2 (descriptive metadata). |
Line 24: source_documents.parent_id “self-FK chain” | Confirmed FK exists, but is ON DELETE SET NULL (inventory implies CASCADE-like by analogy). Minor wording — the chain is preserved via SET NULL not CASCADE. | LOW | Optional: explicitly note SET NULL semantics in the relationships line. |
Line 280: bid_questions column list omits created_by | Actual column exists; inventory missed it. | LOW | Add to column list. |
Line 103: content_history columns “(content_item_id, version, title, content, brief/detail/reference, metadata, change_summary, change_type)“ | Actual columns include change_reason (separate from change_summary) and created_by. Inventory omitted both. | LOW | Add change_reason + created_by. |
Line 711: pipeline_runs column list | Actual columns include items_skipped, items_updated, created_by — inventory omits. | LOW | Add the three columns. |
Line 722: processing_queue column list | Actual columns include result (jsonb) + created_by + idempotency_key (inventory mentions key inside payload envelope; column is explicit). | LOW | Add result and created_by to column list; clarify idempotency_key is a top-level column not just inside payload. |
Line 292: bid_responses columns omit overall_score (numeric 0-100 with CHECK constraint). | Actual column exists. | MEDIUM | Add overall_score. Cascades to ontology doc §3.5 / Finding 05 outcome columns — overall_score already-exists is relevant to the “extend with evaluator_score” recommendation. |
Line 586: taxonomy_domains column list | Actual columns add display_name, key_signal (text); inventory omits. | LOW | Add these. |
Line 593: taxonomy_subtopics column list | Actual adds display_name; inventory omits. | LOW | Add. |
Line 143: classification_disputes.disputed_by / resolved_by references | FKs target user_profiles (with ON DELETE SET NULL), not auth.users directly. Inventory line 144 says “auth.users”. | LOW | Replace auth.users with user_profiles (mirror table) for these specific FKs. Doesn’t change semantics but improves accuracy. |
Line 103 + 1086: content_history --(N:1 SET NULL)--> content_items (relationship map confirms) | The trigger architecture is: content_history.set_content_history_version fires INSERT (auto-version). The “auto-populated by triggers on content_items changes” claim (line 103) is partially right — app code + trg_content_items_ensure_v1_history (INSERT on content_items) drives it, not an UPDATE trigger directly. Minor wording. | LOW | Clarify: app code writes content_history rows; trigger sets the auto-version. |
1.3 Missing from inventory (entities in codebase / docs not captured)
Section titled “1.3 Missing from inventory (entities in codebase / docs not captured)”| Entity | Domain | Why missing matters |
|---|---|---|
feed_articles.extraction_method enum (CHECK: rss_content, fetch, jina_reader, firecrawl, summary_fallback) | Sector intelligence | This is a 5-value Layer-1 CV that belongs in ontology §2.1 (Layer 1 CV scatter). Ontology doc claims “scattered across 24+ artefacts in 5 different homes” — this one was missed. Also relevant to 0.9-context.md §7.5 “drop Firecrawl” planning. |
source_document_diffs.diff_mode enum (qa, full_text) | Source / binary | Another Layer-1 CV — and one with direct relevance to Theme C (edit_intent) / Theme D (cocoindex ops-DB ledger replacing diffs). |
bid_responses.overall_score (numeric 0-100, CHECK constraint) | Bid | Already-exists column relevant to Finding 05’s “extend with evaluator_score” recommendation — inventory’s omission risks Finding 05 proposing a duplicate column. |
quality_issues_pending view (acknowledged at line 949 only) | Operational | Inventory lists it under “operational/supporting” but the view’s join shape isn’t enumerated. Marginal — view is a derived projection. |
content_items.author_name column | Content | Present in actual schema; inventory line 67 lists “Identity” cluster but omits author_name. |
pipeline_runs.items_skipped, items_updated, created_by | Pipeline | All present; inventory omits. Relevant to the pipeline_runs retain-vs-retire decision (RESOLVED-RETAIN per feedback-findings-review §5.2.1). |
taxonomy_domains.display_name, key_signal | Taxonomy | Both present; inventory omits. key_signal may be load-bearing for taxonomy classification confidence. |
processing_queue.result (jsonb) + idempotency_key as a top-level column | Pipeline | Inventory mentions idempotency_key as inside payload envelope; actual schema has it as a top-level column. result jsonb is entirely missed. |
auto_version_content_history() + ensure_v1_history_at_commit() + enforce_archive_state_consistency() triggers | Audit / lifecycle | Inventory line 554 mentions one trigger by name (enforce_archive_state_consistency) but not the auto-version one — this matters because S231’s Theme C edit_intent work-package needs to fit the existing trigger surface. |
1.4 Phantom entities (claimed but not found)
Section titled “1.4 Phantom entities (claimed but not found)”| Claimed entity | Where claimed | Severity |
|---|---|---|
template_requirements.requirement_type='checklist' | Inventory line 443; cascades to ontology §5 rationale | CRITICAL — the ontology disposition stands but the rationale is wrong. |
template_fields.field_type='table_cell' | Inventory line 429 | HIGH — table_cell does not exist. |
template_fields.mapping_status='auto_mapped' | Inventory line 429 | HIGH — not in actual enum. |
bid_questions.status='not_started' / 'ai_drafted' / 'needs_review' | Inventory line 280 | HIGH — none of these three exist in actual enum. |
guides.guide_type='completeness' | Inventory line 571 | MEDIUM — not in actual enum. |
workspaces.status='active' (implied by “draft/active/won/lost/etc.”) | Inventory line 229 | LOW — active is not in actual enum (the enum is the 10 BID_STATES). |
digests.filters + digests.governance_summary columns | Inventory line 534 | HIGH — both phantom; actual is metadata jsonb. |
company_profiles.slug (UNIQUE) | Inventory line 350 | MEDIUM — column exists, but UNIQUE constraint does NOT. |
content_history.change_type ∈ {classify, import, delete} as in-use | Inventory line 103 | MEDIUM — present in enum but none in actual data (zero rows with those values). |
§2 — Ontology pipeline mapping findings
Section titled “§2 — Ontology pipeline mapping findings”2.1 Confirmed correct mappings
Section titled “2.1 Confirmed correct mappings”- §1 Talisman framework recap is accurate to the cited source (no fabrications detected vs Jessica Talisman’s substack framing).
- §2.1 Layer 1 table (27 rows) — entries that match inventory + DB:
taxonomy_domains,taxonomy_subtopics,layer_vocabulary,content_typeenum (15 values),platformenum,lifecycle_type,dedup_status,freshness,governance_review_status,publication_status,ingest_source,BID_STATES,workspaces.type,entity_aliases(with thesaurus-adjacent caveat in §2.4 — correct framing),chunk_kind(planned),scope_tag[](planned),origin_kind(planned),extractor_kind(planned),citation_kind(planned),application_type(NEEDED),form_type(NEEDED),form_format(NEEDED),change_report_category(NEEDED),cocoindex_source_kind(planned). - §2.2 Layer 2 structural / descriptive / administrative / social-provenance categorisation — sample-verified:
embedding vector(1024)(correct: text-embedding-3-large per CLAUDE.md),content_text_hash GENERATED ALWAYS(correct),pipeline_run_id(correct), audit columns (correct),content_historyframing as immutable snapshots (correct conceptually — see 1.2 note re trigger architecture). - §2.3 Layer 3 taxonomy — accurate: 2-level domain → subtopic via FK (no SKOS), self-FK on content_items + content_chunks (correctly framed as asset hierarchy not taxonomy).
- §2.4 Layer 4 thesaurus — correctly identifies
entity_aliasesas flat (no SKOS),entity_relationshipsas misplaced (closer to Layer 5 — see §2.3 below). - §2.5 Layer 5 ontology — class enumeration matches DB tables; “no formal RDF/OWL export” claim correct.
- §2.6 Layer 6 KG — “Planned only” correct; aligns with CX.32 RESOLVED-as-cocoindex per
0.9-context.md§7.5 + S232 ratification.
2.2 Inaccurate mappings
Section titled “2.2 Inaccurate mappings”| Ontology claim | What inventory + code actually shows | Severity | Fix recommendation |
|---|---|---|---|
§2.1 row 11 change_type enum on content_history = “edit, classify, import, archive, delete (5 in use)“ | Actual CHECK: 11 values; actual in-use: archive, create, edit, metadata_change, owner_change. | HIGH | Update to “11 valid values; 5 in active use = archive/create/edit/metadata_change/owner_change”. |
§2.1 row 12 requirement_type enum = “(current values TBD)“ | Actual: 7 values = policy, statement, evidence, data, narrative, declaration, reference. | MEDIUM | Replace “TBD” with the 7-value list. Materially strengthens §5 row “Form requirement_type='checklist' — RESOLVED-NO”. |
§2.1 row 13 ingest_source enum = 11 values | Inventory’s 11-value list matches actual usage; no CHECK constraint exists on the column (it’s a free-text column). Verified: distinct in-use values = 5. | MEDIUM | Clarify: ingest_source is a free-text column with documented canonical values; not enforced by DB. Document as a soft-CV, not a hard enum. Implications for Layer 1 promotion (Build phase 1) — needs a CHECK migration to truly enforce. |
§2.2 administrative metadata: cites digests having governance_summary (implicit in line 121’s framing) | governance_summary does NOT exist on digests. | MEDIUM | Drop the reference; the administrative metadata claim survives via other columns. |
§2.4 row 1 entity_aliases “Surface-form aliases” | Verified — but the ontology doc says “no SYN/BT/NT markup” (correct) AND inventory line 638 + actual schema confirm category enum = (client, generic) (a partial categorisation). Ontology doc could note this partial structure. | LOW | Optional refinement: note the category column as a proto-classification (not full SKOS). |
| §3.1 “24+ artefacts in 5 different homes” | Counting §2.1 rows: 27 artefacts. “24+” is conservative-correct; “5 homes” (DB enums, DB tables, TS const tuples, TS type unions, Zod schemas) is correct. | n/a | OK as-is. |
| §3.7 cocoindex Layer mapping: “@coco.fn(memo=True)“ | Verified against 0.9-context.md §3 (graphify-feedback context); accurate. | n/a | OK. |
2.3 Layer-placement errors (entities at wrong Talisman layer)
Section titled “2.3 Layer-placement errors (entities at wrong Talisman layer)”entity_relationshipsis currently placed in §2.4 (Layer 4 thesaurus, “misplaced”) AND §2.5 (Layer 5 ontology, “partial”). This is internally consistent (the doc explicitly says “closer to Layer 5”) — not an error. The doc correctly proposes promoting it to Layer 5 substrate.BID_STATESis in §2.1 (Layer 1 CV) — correct. §2.3 (Layer 3) notes it’s misplaced AS A TAXONOMY (it’s a sequence not a hierarchy) — that placement-correction is correct. The doc does NOT make a category error here; it explicitly flags the right one.q_a_pairstreated at Layer 5 in §3.5 — correct.feed_articles.extraction_methodandsource_document_diffs.diff_mode— neither appears in the ontology doc Layer 1 because the inventory missed them. Indirect category error caused by inventory gap, not by ontology reasoning. Fix: add both to §2.1 Layer 1 table when inventory is updated.
2.4 Foundational-question (§4) answer trace audits
Section titled “2.4 Foundational-question (§4) answer trace audits”| Question | Trace verdict | Notes |
|---|---|---|
| §4.1 (content_items ↔ workspaces M:N purpose) | TRACED | Inventory line 245 confirms content_item_workspaces (81 rows). Workspaces are 4 (all intelligence) — so M:N is conceptually right but empirically untested across workspace types today. Ontology answer (“knowledge-artefact-to-application-instance assignment”) is sound; the “examples from data inventory §4 matrix” (line 326) reference real planned applications but not yet observed in prod data (since only intelligence workspaces exist). Caveat: the cited example “a Phew capability statement cited in a bid response” is hypothetical, not observed in prod. |
| §4.2 (applications layer above workspaces) | TRACED | Aligns with feedback-findings-review §5.1 Theme E “RESOLVED” + Prereq 1 §4.2 closure. Option (a) application_types CV recommendation is consistent with inventory line 66 (application_type NEEDED). |
| §4.3 (product_guide BOTH content and application) | TRACED | Inventory line 569 confirms guides table (11 rows) + guide_sections (135). Ontology’s “both, orthogonal axes” answer is consistent with inventory line 896 entry “Product guides (Phew use case — application or content)” framed as unclear, and feedback-findings-review §5.1 Theme E. |
| §4.4 (Q&A pairs form-agnostic implications) | PARTIAL | Ontology recommends “new q_a_pair_workspaces junction” (line 392) — but inventory line 187 spec says q_a_pairs.workspace_id direct FK (“N:1 → workspaces”). Contradiction — see §3 below. Either q_a_pairs are 1:N to workspace (current spec) or M:N via junction (ontology recommendation). The “form-agnostic” framing itself traces correctly; the workspace-relation shape is what diverges. |
| §4.5 (form-type = type + format split) | TRACED | Maps to inventory lines 66 (form_type NEEDED), 68 (form_format NEEDED), 415 (templates planned rename to form_templates), 442 (template_requirements rename), and feedback-findings-review §5.1 Theme A “RESOLVED”. checklist framing as form-format (not requirement-type) is directionally correct but built on the inventory’s phantom requirement_type='checklist' claim (see §1.4) — the underlying decision is robust; the rationale text needs amending once inventory is fixed. |
2.5 Cross-references back to feedback-findings-review.md §5
Section titled “2.5 Cross-references back to feedback-findings-review.md §5”Spot-check of ontology doc §5 RESOLVED items vs canonical disposition state (feedback-findings-review.md §5.2 + §5.3):
| Ontology §5 item | Canonical disposition state | Match? |
|---|---|---|
Applications layer = Option (a) application_types CV | feedback §5.1 Theme E RESOLVED | ✓ MATCH |
form / form-type / form-format entity definitions = two Layer-1 CVs | feedback §5.1 Theme A RESOLVED + §5.3.1 row 2 RESOLVED | ✓ MATCH |
source_documents vs cocoindex source-key = Option α (slim-and-keep) | feedback §5.2.1 row 1 RESOLVED-DIRECTIONAL: Option α | ✓ MATCH |
content_items vs q_a_pairs boundary — peer classes | feedback §5.3.1 row 4 RESOLVED — peer classes | ✓ MATCH |
product-guide as application vs content type = both | feedback §5.3.1 row 5 RESOLVED — both | ✓ MATCH |
| Citer space for citations = polymorphic citing_entity | feedback §5.2.2 row 3 + §5.3.1 row 6 RESOLVED | ✓ MATCH |
template_requirements rename = form_template_requirements | feedback §5.2.3 row 2 + §5.3.1 row 7 RESOLVED | ✓ MATCH |
requirement_type='checklist' = NO, fold into existing | feedback §5.2.4 row 5 + §5.3.1 row 8 RESOLVED — NO | ✓ MATCH (modulo phantom-enum rationale) |
Finding 05 = bid_workspaces Option B satellite | feedback §5.2.5 + §5.3.1 row 9 RESOLVED-DIRECTIONAL — Option B | ✓ MATCH |
| Per-type satellite = per application_type vocab entry | feedback §5.2.3 row 4 + §5.3.1 row 10 RESOLVED | ✓ MATCH |
edit_intent Layer-1 CV (cosmetic/data/structural) | feedback §5.1 Theme C RESOLVED-DIRECTIONAL | ✓ MATCH |
Verdict §2.5: all 11 spot-checked dispositions are internally consistent between the ontology doc and the canonical feedback-findings-review §5. No drift detected.
§3 — Cross-doc contradictions
Section titled “§3 — Cross-doc contradictions”| Inventory claim | Ontology doc claim | Severity | Resolution recommendation |
|---|---|---|---|
Inventory line 181: q_a_pairs “workspace_id” attribute (N:1 → workspaces) | Ontology §4.4 line 392: “new q_a_pair_workspaces junction, because q_a_pairs are no longer subtypes of content_items — they’re a peer class” (M:N) | MEDIUM | Pick one. Sit-down required: the M:N recommendation is consistent with the form-agnostic framing (a Q&A pair may serve multiple workspaces); the 1:N spec inherited from 0.9-intended-architecture.md §4.3 is simpler. Recommend: adopt M:N to honour Theme A form-agnosticism + match content_items pattern. Propagate to 0.9-intended-architecture.md §4.3. |
Inventory line 443: template_requirements.requirement_type enum lists (declaration/evidence/checklist) | Ontology §5 line 458: “RESOLVED-DIRECTIONAL — NO, fold into existing declaration / evidence. Checklist is a form_FORMAT not a requirement_TYPE.” | HIGH (rationale mismatch) | The decision is internally consistent — but the ontology’s rationale assumes inventory’s claim was correct. Once inventory is fixed (requirement_type has 7 values, no checklist), the ontology’s reasoning text needs amending: “the existing 7-value taxonomy (policy, statement, evidence, data, narrative, declaration, reference) is sufficient; checklist is a form_FORMAT not a requirement_TYPE — adding a new value is not needed.” |
Inventory line 67: content_items.content_type “(slated to move out per Q3): answer_standard, answer_advanced” | Ontology §3.5 line 287-293: q_a_pairs peer class, citers via polymorphic relation | LOW | Consistent intent; minor wording drift in inventory (q_a_pair COLUMNS slated to move, not the content_type itself). |
| Inventory line 569: guides.guide_type = “sector/product/company/research/custom/completeness” | Ontology doesn’t reference completeness value | LOW | completeness is a phantom in inventory (see §1.4) — ontology is silent which is correct. |
Inventory line 229: workspaces.type = “(bid/kb_section/intelligence — CHECK); plus proposal-placeholder in code registry” | Ontology §2.1 row 14: workspaces.type discriminator (CHECK) — “(bid / kb_section / intelligence (DB); plus proposal-placeholder in code registry)“ | LOW | Consistent; the “code registry” reference is unsourced. Verified proposal-placeholder is not in DB CHECK; if it’s in TS code only that’s fine but needs a file pointer for traceability. |
| Inventory line 632: entity_relationships “relationship_type 10-value enum (holds/…/evidences)“ | Ontology §2.5 line 226: notes entity_relationships is “partial ontology” — agrees that relationship_type is typed. | n/a | No contradiction. |
§4 — Overall verdict
Section titled “§4 — Overall verdict”Inventory verdict: PASS-WITH-NOTES. The structural inventory (entity catalogue, relationship map, application-to-data matrix) is well-organised and broadly accurate. Row counts are all correct. The lifecycle-stage taxonomy is consistent with 0.9-intended-architecture.md and the feedback-findings-review §5 disposition state. The inaccuracies cluster in enum value lists — six entities have enum values that diverge from the actual DB CHECK constraints, with template_requirements.requirement_type and bid_questions.status and template_fields.field_type/mapping_status being the most consequential. Plus the digests column-list phantoms (filters, governance_summary) are wrong. None of these change the architectural decisions, but they cascade into ontology §2.1 and §5 rationales.
Ontology pipeline verdict: PASS-WITH-NOTES. The Talisman framework recap is faithful. The Layer 1-6 mapping is conceptually sound, with the correct insight (“KH jumps from Layer 1 to Layer 5, skipping the Metadata-Standard / Taxonomy / Thesaurus formalisations”). All 11 spot-checked §5 dispositions match feedback-findings-review §5 canonical state. The §4 foundational-question answers all trace except §4.4 (q_a_pair workspace-relation cardinality — M:N junction vs 1:N FK is the one substantive contradiction with inventory). The §5 RESOLVED items are correctly placed but a few inherit the inventory’s phantom-enum claims as rationale rather than premise.
Confidence: 88%. High structural quality across both docs; the inaccuracies are at the enum-value detail level where they cascade most into Build Phase 1 (CV consolidation) — easy to fix in one pass.
Top-3 fixes required before propagation to Phase 3 docs:
- Rewrite enum value lists in inventory (lines 103, 280, 429, 443, 534, 571) and the corresponding ontology §2.1 + §5 cells. Critical for any spec that consumes these enums (especially Build Phase 1 vocabulary register).
- Decide q_a_pair → workspace cardinality (M:N junction vs 1:N FK). The inventory says 1:N; the ontology recommends M:N. Pick one and propagate. Recommend M:N for Theme A form-agnostic consistency.
- Update
digestscolumn claim (dropfilters,governance_summary; addmetadata). Propagates to ontology §2.2 administrative-metadata enumeration.
Top-3 fixes that can defer to next session:
- Add the missing enum CVs to ontology §2.1 (
feed_articles.extraction_method,source_document_diffs.diff_mode). Strengthens the “vocabulary scatter” §3.1 count slightly (24+ → 29+) but doesn’t change strategy. - Add
company_profilesmissing columns (is_active,is_primary,company_embedding) and the absent slug-UNIQUE constraint claim correction. - Document the auto-version trigger architecture on
content_historymore precisely (vs the current “auto-populated by triggers on content_items” hand-wave).
§5 — Methodology
Section titled “§5 — Methodology”What I did:
- Cross-referenced all 30 row-count claims in inventory §1 against live DB queries (
mcp__supabase__execute_sqlonrovrymhhffssilaftdwd). All 30 verified. - Sampled CHECK constraint definitions for 22 enum-bearing columns; compared each against the inventory’s enumeration. Six enums diverged (the §1.2 + §1.4 findings).
- Verified the complete public-schema table set (46 tables + 1 view) is captured by inventory; no missing tables.
- Sampled 12 column-list claims (the most consequential entities); identified 9 column-list inaccuracies (mostly omissions, two phantoms).
- Verified all FK direction claims in
relationship map§2 for 9 tables; all correct. - Verified all code-domain claims for
lib/subdirs (19 subdirs),app/api/cron/(9 dirs),mcp-apps/(4 dirs),lib/mcp/tools/(18 files),types/(12 files). All correct. - Cross-checked ontology doc §5 RESOLVED items (11 items) against
feedback-findings-review.md§5 (canonical disposition register). All 11 match. - Spot-checked ontology §4.1-§4.5 answer reasoning traces against inventory entities. 4 fully traced; §4.4 has the one substantive cardinality contradiction noted in §3.
- Verified
content_text_hashGENERATED ALWAYS expression directly viainformation_schema.columns. Confirmed. - Verified trigger inventory via
information_schema.triggerson content_items + content_history + workspaces. Two architectural claims clarified (§1.2 line 21). - Verified
feed_articles.external_urlUNIQUE-per-workspace is implemented as a unique index (idx_feed_articles_dedup), not as a table-constraint. Inventory claim is correct despite being non-obvious ininformation_schema.table_constraints.
What I skipped:
- Detailed audit of every column on every table. Sampled the consequential entities; did not verify every column for low-traffic tables (e.g.
coverage_targets,governance_config). - Verification of every code claim in
types/files (only sample-verified that the files exist + general shape). - RLS policy verification (out of scope for accuracy audit; would be a separate security audit).
- Lifecycle-stage validation for every single entity. Sampled ~10 against
0.9-intended-architecture.md§1.2 + feedback-findings-review §5; all matched. - Python pipeline (
scripts/kb_pipeline/) file-list verification. Inventory line 738 lists ~18 files; sampled existence checks only. - Verification of every claim in the application-to-data matrix (§4 of inventory). The matrix is conceptual / forward-looking; current prod data (4 intelligence workspaces) wouldn’t validate cross-application claims empirically.
- MCP tool count verification (“54 tools” claim) — counted 16 categories matching the inventory; trusted the tool count without enumerating.
Caveats:
- Live DB is prod (
rovrymhhffssilaftdwd), not staging. Production state is the source of truth for the inventory’s intent. - Row counts are point-in-time (13/05/2026). Numbers like q_a_pairs (395) may drift before propagation; the magnitude is what matters.
- Trigger introspection looked only at
information_schema.triggers— there may be RPC-layer behaviours that look trigger-like at app level. Out of scope. - The “soft FK” pattern (e.g.
governance_config --(N:1 logical)--> taxonomy_domainsvia domain text) was not separately verified; inventory’s relationship map is the authoritative claim and was used as-is.
End of verification report. Recommended action: apply the §1.2 + §1.4 enum-list corrections to inventory in a single pass; update ontology §2.1 + §5 cells that inherit those values; resolve the §3 q_a_pair workspace cardinality contradiction. After those fixes, both docs are propagation-ready for 0.9-decision-graph.md / 0.9-collapse-candidates.md / 00-synthesis-v2.md.