KB-5428 rev 2

P9 E1–E3 Read-only Design Pack v0.2

9 min read Revision 2

E1–E3 Read-only Design Pack v0.2

Phase: P9 Entry Gate, E1–E3 Trạng thái: DRAFT v0.2 — Patched 3 điểm GPT. Chờ GPT final + User. Ngày: 2026-04-27 | Phiên: S182


E1 — fn_log_issue / system_issues (COMPLETED)

Result: PASS — adapter feasible without ALTER.

Full report: knowledge/draft/p9-e1-fn-log-issue-verify-2026-04-27.md

Key: fn_log_issue = plain INSERT, no dedup, severity chỉ critical/warning/info, không ghi coalesce_key.


R3 — Checker Adapter Design (dựa trên E1)

R3.1 Wrapper contract

fn_tac_log_checker_issue(
    p_checker_id  TEXT,     -- P6 checker ID, e.g. 'DOT-LU-01'
    p_severity    TEXT,     -- P6 vocabulary: BLOCK/ERROR/WARN/INFO
    p_entity_code TEXT,     -- canonical_address
    p_summary     TEXT,     -- finding summary
    p_details     JSONB DEFAULT NULL
) RETURNS INTEGER

R3.2 Field mapping contract (full chain)

P6/P8 field Wrapper param fn_log_issue param system_issues column Dedup key?
checker_id p_checker_id p_source source ✅ YES
severity p_severity p_severity (mapped) severity
category p_checker_id p_issue_type issue_type
entity_code p_entity_code p_entity_code entity_code ✅ YES
summary p_summary p_title title
details p_details p_evidence evidence_snapshot
issue_signature (computed) coalesce_key (backfill) ✅ YES (= dedup key itself)

R3.3 Dedup contract (cụ thể)

Dedup key definition:

coalesce_key = md5(p_checker_id || '|' || p_entity_code)

Rationale: Cùng checker + cùng entity = cùng violation. Severity/summary có thể thay đổi giữa runs nhưng violation identity không đổi.

Dedup logic trong wrapper:

-- Step 1: Compute dedup key
v_dedup_key := md5(p_checker_id || '|' || p_entity_code);

-- Step 2: Check existing open issue with same key
SELECT id, severity INTO v_existing_id, v_existing_severity
FROM system_issues
WHERE coalesce_key = v_dedup_key AND status = 'open'
LIMIT 1;

-- Step 3a: Existing → UPDATE (escalate severity + refresh timestamp)
IF v_existing_id IS NOT NULL THEN
    UPDATE system_issues SET
        last_seen_at = NOW(),
        occurrence_count = COALESCE(occurrence_count, 1) + 1,
        severity = CASE
            WHEN v_mapped_severity_rank > v_existing_severity_rank
            THEN v_mapped_severity
            ELSE severity
        END,
        title = p_summary,           -- refresh summary
        evidence_snapshot = p_details -- refresh evidence
    WHERE id = v_existing_id;
    RETURN v_existing_id;
END IF;

-- Step 3b: New → INSERT via fn_log_issue + backfill coalesce_key
v_new_id := fn_log_issue(
    p_checker_id,           -- source
    v_mapped_severity,      -- severity (mapped)
    p_summary,              -- title
    NULL,                   -- description
    'tac_logical_unit',     -- entity_type (or derive from checker)
    p_entity_code,          -- entity_code
    p_checker_id,           -- issue_type = checker_id
    p_details,              -- evidence
    NULL,                   -- run_id
    'open'                  -- status
);

-- Backfill coalesce_key (fn_log_issue doesn't write it)
UPDATE system_issues SET coalesce_key = v_dedup_key WHERE id = v_new_id;

RETURN v_new_id;

R3.4 Severity mapping

P6 vocabulary Wrapper maps to fn_log_issue accepts
BLOCK critical
ERROR critical
WARN warning
INFO info

Severity rank for escalation: critical=3, warning=2, info=1.

R3.5 Dedup guarantees

Guarantee Mechanism
Same checker + same entity = 1 open issue coalesce_key = md5(checker|entity) + SELECT before INSERT
Severity only escalates, never downgrades CASE rank comparison
occurrence_count tracks frequency INCREMENT on existing
latest finding reflected UPDATE title + evidence on existing
resolved issues don't block new detection WHERE status = 'open' filter

R3.6 Execution note

Wrapper = DDL (CREATE FUNCTION). Thuộc E-R3 execution — cần prompt riêng + GPT/User approval. Không tạo trong E1–E3 pack.


E2 — Đ24 Facet Reconciliation Design

2.1 Candidate proposal (NOT default)

FAC-07/08/09 là candidate theo pattern hiện có. APR có quyền approve/modify/reject.

Alias Candidate code Candidate name Status
doc FAC-07 Thuộc tài liệu nào? Candidate — chờ APR
topic FAC-08 Chủ đề nội dung? Candidate — chờ APR
layer FAC-09 Tầng kiến trúc? Candidate — chờ APR

No APR = no facet creation. APR có thể:

  • Approve FAC-07/08/09 as proposed
  • Modify code/name (e.g. FAC-07→FAC-DOC nếu Council quyết)
  • Reject (nếu dùng facet hiện có tốt hơn)

2.2 Governed flow

DOT-TAC-LABEL-FACET-VERIFY
  → detect missing → system_issues (via fn_tac_log_checker_issue)
  → create APR request_type='create_taxonomy_facet'
    proposed_action: INSERT taxonomy_facets (code='FAC-07', ...)
  → User/Council approve/modify/reject
    → If approved → DOT-TAC-LABEL-SYNC via Directus API POST
    → Re-verify

2.3 Label values

Facet Values pilot Notes
FAC-07 (doc) D38-HOWTO, D38-C1A, D38-P5 3 values
FAC-08 (topic) guide, segmentation, schema 3 values
FAC-09 (layer) design 1 value

Values registration: verify taxonomy_labels table exists trước execution.

2.4 P8 amendment

P8 §5: "doc/topic/layer = alias. Production dùng facet_id FK → taxonomy_facets. Facet codes = APR outcome."


E3 — D38 Entity Code Format Contract

3.1 Scope: LOCAL contract only

D38-domain contract cho TAC canonical_address. KHÔNG phải global Đ24 standard. Đ24 global format = separate OD nếu sau này cần.

Ghi cứng: contract này KHÔNG lan thành chuẩn toàn hệ thống. Mỗi domain tự chốt entity_code convention.

3.2 Contract

D38 Text as Code entity_code convention:
- entity_code = tac_logical_unit.canonical_address (verbatim)
- LOCAL D38-domain contract, NOT global Đ24 standard
- Regex: ^D38-[A-Z0-9]+-((ROOT)|(S[0-9]+(-P[0-9]+(-[0-9]+)*)?))$
- Covers:
    D38-HOWTO-ROOT          (root)
    D38-HOWTO-S1            (section)
    D38-C1A-S4-P1           (paragraph)
    D38-C1A-S4-P1-1         (deep nesting, future)
- Character set: uppercase alphanumeric + hyphen
- Length: 10–30
- UNIQUE: tac_logical_unit.canonical_address constraint
- Prefix: D38-

3.3 Validation

DOT-TAC-LABEL-FORMAT-VERIFY: query all canonical_address, match regex. Any miss = FAIL.

76 pilot units: all match D38-{DOC}-(ROOT|S{n}|S{n}-P{n}). Regex covers.


Summary

Step Status Next
E1 fn_log_issue ✅ PASS verified
R3 adapter design ✅ DESIGN v0.2 (dedup contract) E-R3 execution (approval)
E2 Đ24 facets ✅ DESIGN v0.2 (candidate, not default) E4 APR (approval)
E3 entity_code ✅ DESIGN v0.2 (local D38 only) P8 amendment

All design-only. No DDL/DML. No production mutation.

Execution roadmap (chờ review)

Phase Scope Mutate?
E-R3 Create fn_tac_log_checker_issue wrapper ✅ DDL
E-E3 Amend P8 §5 (entity_code + alias) ❌ doc
E4 APR request FAC-07/08/09 ✅ APR
E5 If approved → create facets ✅ taxonomy
E6 Re-run Tier 1 A1–A3 ❌ read-only
E7 dot-dot-register v2 D1–D3 dry-run
E8 dot-dot-register v2 D4 register ✅ dot_tools

Mỗi mutate step = prompt riêng + GPT review.


Patch log v0.1 → v0.2

# GPT điểm Sửa
1 R3 dedup key contract coalesce_key = md5(checker_id|entity_code). Full dedup logic: SELECT existing → UPDATE or INSERT+backfill. Severity escalation. occurrence_count.
2 E2 facets = candidate not default ✅ FAC-07/08/09 = candidate. APR can approve/modify/reject. No APR = no creation.
3 E3 entity_code = local D38 only ✅ Ghi cứng: local contract, KHÔNG lan thành global Đ24 standard.

E1–E3 Design Pack v0.2 | S182 | 2026-04-27 | Opus 4.6 GPT: v0.1 PASS CĐK (3) → v0.2 patched Chờ GPT final + User