Phase 1 Data Model — schema, model & DRG-shape changes
This mission changes no runtime storage. The "entities" are doctrine schema / model shapes and DRG projection rules. Each change below is a boundary made single-sourced or fail-loud.
E1 — _DRG_NODE_KINDS (derived set) [IC-1, #3608]
topic_resolver.py:37 (drifted 6 kinds vs NodeKind).
— exact equality (fails on missing and extra).
(if lhs not in _DRG_NODE_KINDS: return None). Post-change, every canonical kind (incl. glossary_pack, mission_step_contract, anti_pattern, asset, glossary, template) is recognized.
- Before: hand-maintained
frozenset[str]literal in - After:
_DRG_NODE_KINDS: frozenset[str] = frozenset(k.value for k in NodeKind). - Invariant (pinned by drift-guard test):
_DRG_NODE_KINDS == {k.value for k in NodeKind} - Consumer: membership gate at
topic_resolver.py:236
E2 — ContextSources / AgentContextSources / profile schema [IC-2, #3629 p1]
context-sources with subfields directives, tactics, toolguides, styleguides, doctrine-layers, additional (all list[str]).
profile.py::ContextSources (and its attribute on AgentProfile), schema_models.py::AgentContextSources, and the JSON schema. Because both models use extra="forbid", a profile still authoring context-sources is rejected at load (fail-loud) — the desired boundary.
— directive-references, tactic-references, toolguide-references, styleguide-references (structured {id, rationale} / DirectiveRef).
- Before (both pydantic models +
agent-profile.schema.yaml): field - After:
context-sourcesblock removed entirely from - Canonical surface (retained/authoritative): top-level
*-references - Migration mapping (upgrade migration + the 25 shipped profiles):
toolguides/styleguides preserved); delivered content to a dispatched agent is unchanged (C-006).
- Invariant: no authored artefact reference is lost (directives/tactics/
from context-sources.* | to |
|---|---|
directives | directive-references (id, keep any rationale) |
tactics | tactic-references |
toolguides | toolguide-references |
styleguides | styleguide-references |
additional | dropped (freeform, no artefact/edge target) |
doctrine-layers | dropped (layer names, no NodeKind) |
E3 — agent_profile DRG projection (extractor) [IC-2, #3629 p1]
(extractor.py:920-929) and top-level tactic-references→requires→tactic (:930-942).
→ requires → directive (replacing the context-sources.directives loop); tactic-references unchanged; add toolguide-references/styleguide-references → suggests (or requires) → toolguide/styleguide when authored.
content that was already delivered; net-new edges only for previously-inert authored refs now carried on *-references.
- Before: extractor projects
context-sources.directives→requires→directive - After: projects from the
*-referencessurface uniformly —directive-references - Invariant: the set of DRG edges minted for a given profile is unchanged for
E4 — governance-profile scope edges (fail-loud) [IC-3, #3629 p2]
raises on any selected_* target that is not a minted node (built-in path, tested). Verify the org-tier governance-profile path is equally guarded.
both built-in and org tiers; valid selections mint scope edges unchanged.
- State:
assert_governance_scope_edges_resolve(extractor.py:1406) already - Invariant (target end-state): a nonexistent
selected_*id fails loud on
E5 — load_validated_graph org seams [IC-4, #3530]
merge_three_layers. org_roots= (_drg_helpers.py:138-182) reads only root *.graph.yaml, ignores drg/fragment.yaml, and suppresses the "no graph" warning when a fragment exists (:174). Callers executor.py:362 and action_doctrine_bundle.py:192 pass only org_roots → silent drop.
two callers thread org_fragments), and the warning is honest (no false suppression). No double-fold when both org_roots and org_fragments are given.
a genuinely missing DRG produces a real warning.
- Before: two seams.
org_fragments=foldsdrg/fragment.yamlvia - After: the
org_roots=seam also loadsdrg/fragment.yamlper root (or the - Invariant: an org pack's declared nodes/edges reach every consumer seam;
E6 — packs/internal/ (fixture) [IC-4/IC-5, #3530]
the on-disk directives/ dir + OPERATOR_SIGNAL_CONTRACT node.
procedures (landing-contributor-prs), directives (OPERATOR_SIGNAL_CONTRACT), and refines edges to built-in procedure:red-main-release-discipline / tactic:pr-agent-worktree-isolation.
- Structure: already conformant — no shape change. README refreshed to list
- Role: #3530 chain-delivery fixture (built-in layer 0 + internal org layer 1).
- Declared kinds to verify delivered:
glossary_packs(spk-internal-glossary),
E7 — extractor doc-nit [IC-6, #3629 p3]
to match the M2 WP04 re-ledger reality. No behaviour change.
- Docstring at
extractor.py:557("no golden-count update was required") clarified