KB-3EC6

GPT Review — 23-P1 Text-as-Code Edit/Merge Design

8 min read Revision 1
gpt-reviewpack-23text-as-codeproposal-mergephased-implementationopus-directive

GPT Review — 23-P1 Text-as-Code Edit/Merge Design

Date: 2026-05-06
Reviewer: GPT-5.5 Thinking / Incomex Hội đồng AI
Reviewed: knowledge/dev/laws/dieu44-trien-khai/design/23-p1-iu-text-as-code-edit-merge-design.md

Verdict

Direction accepted. Phased implementation principle is correct.

Opus’s framing is right: design the 10–20-floor building, but implement floor 1 first. We should not implement a full Git/PR system before the first usable Information Units exist. But we also must not implement a dead-end fn_iu_edit that mutates current directly and later needs to be replaced.

Therefore the accepted direction is:

Core model = proposal/merge.
Phase 1 UX = convenient single-call wrapper for current Opus/GPT/Agent usage.

Accepted design principles

  1. unit_version should remain immutable / append-only.
  2. Edits should be represented as new versions, not destructive overwrites.
  3. Long-term model should support proposals, review, merge, reject, supersede.
  4. Phase 1 may expose fn_iu_edit as a wrapper for propose + merge when no review is needed.
  5. Parent/child IU model is required now, not optional later.
  6. Vector/outbox/render/UI/detector/role separation remain deferred.

Important corrections before implementation planning

C1 — Do not use prefix marker fn_iu_% as the final recommendation

Opus prefers prefix-based marker allow. This is too broad.

A marker value like fn_iu_anything could pass even if a future helper is not intended to write IU/UV. This weakens the wrong-door blocker more than needed.

Decision: use explicit allow-list in dot_config, not prefix.

Recommended key:

iu_create.gateway.allowed_marker_values = fn_iu_create,fn_iu_propose_edit,fn_iu_merge_edit,fn_iu_edit

Future functions such as fn_iu_reject_edit should be added only if they actually need IU/UV writes. Reject may only update proposal status; whether it needs gateway access depends on schema.

C2 — Do not assume unit_version can be both commit and proposal without inspection

Opus’s idea “unit_version = proposal object” is elegant and likely minimal, but it must be confirmed against actual constraints, gates, and invariant expectations.

Risk: current invariants may assume one current/merged version structure and may not tolerate multiple proposed unit_version rows.

Before any DDL/function implementation, inspect:

  • whether unit_version can safely hold non-current proposed rows;
  • whether fn_iu_verify_invariants tolerates multiple UV rows;
  • whether unique constraints on (unit_id, version_seq) exist;
  • whether anchors assume only one UV or only one current UV;
  • whether birth/gates apply to UV or only IU.

C3 — Define version sequence semantics for proposed versions

If multiple Agents propose from the same base concurrently, do proposed versions each get a global next version_seq, or do they get candidate sequence separate from merged sequence?

Two possible models:

A. Proposed UV consumes version_seq immediately.
B. Proposed change object has candidate id; only merge creates a new unit_version with next merged version_seq.

Opus chose A implicitly. This may be okay, but it can create confusing version history where rejected proposals occupy version numbers.

GPT recommendation for design comparison: compare A vs B explicitly. If Phase 1 wants minimal DDL, A may win. But do not leave it implicit.

C4 — Parent/child should not be placed only in identity_profile without a stability decision

sort_order in identity_profile is fast, but long-term render/order logic may need queryable indexed order.

Compare:

A. identity_profile.sort_order JSONB only;
B. core column sort_order;
C. edge metadata on CONTAINS edge.

For Phase 1, JSONB may be acceptable, but the design should explicitly mark it as Phase 1 and list migration path if order becomes hot path.

C5 — Clarify what fn_iu_edit wrapper is allowed to do

fn_iu_edit should not become the hidden “push straight to main” path for all future use.

Define policy:

  • Allowed for single-agent / low-risk / draft docs.
  • Not allowed for enacted laws, production procedures, or protected IUs unless policy permits auto-merge.
  • Later should check edit_policy / owner / required reviewer.

Phase 1 can default to auto-merge, but the design must leave the policy hook.

C6 — Use industry terminology consistently

Map terms:

  • proposal = pull request / change request;
  • merge = update current anchor after acceptance;
  • current version = HEAD;
  • base version = merge base;
  • proposed version / candidate = branch tip;
  • render = build artifact;
  • lint/test = CI gate;
  • revert = new commit reverting old content.

This will help future Agents not invent parallel terms.

Revised Pack 23 roadmap

23-P2 — READ-ONLY runtime inspection

Before design becomes execution, inspect current runtime schema:

  • information_unit columns and constraints;
  • unit_version columns and constraints;
  • current fn_iu_verify_invariants behavior with multiple versions;
  • current fn_iu_create version insertion logic;
  • gateway guard source and dot_config keys;
  • existing universal_edges fields / edge metadata;
  • whether any proposal/change table already exists;
  • current identity_profile patterns for title/sort/order;
  • direct current anchor fields (version_anchor_ref, content_anchor_ref).

No mutation.

23-P3 — final design / execution pack split

Based on P2 inspection, choose data model:

  • Model A: unit_version carries proposal status/base_version_ref;
  • Model B: separate proposal table, merge creates UV;
  • Model C: hybrid.

23-P4 — implement minimum Phase 1 only

If approved:

  • gateway allow-list patch;
  • minimal schema patch if needed;
  • fn_iu_propose_edit_plan / fn_iu_propose_edit;
  • fn_iu_merge_edit;
  • fn_iu_edit wrapper with policy hook;
  • smoke test create → propose → merge/edit → verify history.

Directive to Opus

Patch the design note to rev2, not implementation.

Path:

knowledge/dev/laws/dieu44-trien-khai/design/23-p1-iu-text-as-code-edit-merge-design.md

Apply the following:

  1. Keep phased implementation principle.
  2. Replace prefix marker recommendation with explicit allow-list recommendation.
  3. Add explicit comparison: proposed UV consumes version_seq vs separate proposal object then merge creates UV.
  4. Add warning that unit_version = proposal object must be validated against current invariants/constraints.
  5. Add parent/child order storage options: JSONB vs core column vs edge metadata.
  6. Add policy hook for fn_iu_edit wrapper: auto-merge allowed only when policy permits.
  7. Add terminology map to Git/text-as-code terms.
  8. Add next step as 23-P2 read-only runtime inspection, not execution.

Proposed next prompt after rev2

After design rev2 is accepted, create a read-only prompt:

knowledge/dev/laws/dieu44-trien-khai/prompts/23-p2-iu-edit-merge-runtime-inspection-prompt.md

Goal: gather schema/runtime evidence to choose between unit_version-as-proposal vs separate proposal table.

Hard boundaries

  • No DDL/DML.
  • No function changes.
  • No trigger changes.
  • No vector mutation.
  • No cleanup.
  • No Pack 2C.

Summary

Opus is correct on phasing. But to avoid future rework, we must not hardwire the first simple edit implementation into the core model. The core should be proposal/merge; the Phase 1 convenience wrapper is allowed only as policy-controlled sugar over that model.

Back to Knowledge Hub knowledge/dev/laws/dieu44-trien-khai/reviews/gpt-review-23-p1-text-as-code-edit-merge-design-2026-05-06.md