Skip to content

feat(apm): redesign primitives-architect with design discipline + runtime-affordance layering#939

Open
danielmeppiel wants to merge 3 commits intomainfrom
apm-primitives-architect-redesign
Open

feat(apm): redesign primitives-architect with design discipline + runtime-affordance layering#939
danielmeppiel wants to merge 3 commits intomainfrom
apm-primitives-architect-redesign

Conversation

@danielmeppiel
Copy link
Copy Markdown
Collaborator

@danielmeppiel danielmeppiel commented Apr 25, 2026

Redesign apm-primitives-architect: design discipline + runtime-affordance layering

TL;DR

The current apm-primitives-architect is a style/lint auditor. It has no notion of agentic architecture: no runtime mental model, no threading semantics, no orchestration patterns, no separation-of-concerns discipline. The smoking gun is apm-review-panel: 5+ independent lenses crammed into a single sequential loop, when the textbook answer is fan-out + parent synthesizer.

This PR splits the persona into:

  1. A durable architect persona (.apm/agents/apm-primitives-architect.agent.md) carrying only timeless principles: runtime stack mental model, persona-vs-thread disambiguation, classic SW principles applied to prompts, design discipline steps, anti-patterns.
  2. A new apm-primitives-architecture skill that drives a 7-step process and loads modular assets on demand, including a layered runtime-affordances module (common substrate + per-harness adapters for Copilot, Claude Code, Cursor, OpenCode, Codex).

These files are for LLMs to execute, not humans to read. Every byte spent biases inference; every load is a token budget hit. The architecture reflects that.


Why

The problem in one diagram

flowchart LR
    Today[apm-primitives-architect today<br/>style/lint auditor] -->|reviews| Output[Markdown style:<br/>headings, bullets, line length]
    Today -.->|cannot reason about| Missing[Threading<br/>SoC<br/>Orchestration<br/>Portability<br/>Token budgets]
    Missing --> Symptom[apm-review-panel:<br/>6 lenses, single loop,<br/>attention degradation]

    classDef bad fill:#fdd,stroke:#900
    classDef gap fill:#ffd,stroke:#990
    class Today bad
    class Missing,Symptom gap
Loading

Concretely, the architect today cannot answer:

  • Should this be one prompt or N spawned threads?
  • Where is the boundary between persona scoping and skill activation?
  • What runtime concept does this primitive map to, and is the design portable across harnesses?
  • Which assets must load eagerly vs lazily to respect the SKILL.md budget?

The conflation that causes most bugs

Agentic design conflates two orthogonal things that share the word "subagent":

flowchart TB
    subgraph Persona ["PERSONA SCOPING (text loaded into a thread)"]
        P1[".agent.md file"] --> P2["Biases inference of<br/>the thread that loads it"]
        P2 --> P3["Same context window"]
    end

    subgraph Spawn ["CHILD-THREAD SPAWN (runtime concurrency)"]
        S1["Parent calls spawn(...)"] --> S2["Fresh context window<br/>isolated work"]
        S2 --> S3["Returns result to parent"]
    end

    Persona -. orthogonal .- Spawn

    classDef persona fill:#dfd,stroke:#090
    classDef spawn fill:#ddf,stroke:#009
    class P1,P2,P3 persona
    class S1,S2,S3 spawn
Loading

A child thread may load a persona file. A persona file does not spawn anything. Designs that confuse these produce single-loop monoliths with persona swaps disguised as parallelism — exactly what apm-review-panel does today.


What

Module shape

flowchart TB
    Persona[".apm/agents/apm-primitives-architect.agent.md<br/>DURABLE PERSONA<br/>runtime mental model, principles, anti-patterns"]

    subgraph Skill ["apm-primitives-architecture skill"]
        SkillMD["SKILL.md<br/>7-step design discipline"]
        Patterns["assets/architecture-patterns.md<br/>P1-P6 + selection heuristic"]
        Mermaid["assets/mermaid-conventions.md<br/>diagram-per-step + GitHub gotchas"]
        Worked["assets/worked-example-review-panel.md<br/>single-loop -> fan-out before/after"]

        subgraph Affordances ["assets/runtime-affordances/"]
            Common["common.md<br/>5 substrate concepts"]
            Rules["portability-rules.md<br/>declaration + open-closed"]

            subgraph PerHarness ["per-harness/"]
                Copilot["copilot.md"]
                Claude["claude-code.md"]
                Cursor["cursor.md"]
                OpenCode["opencode.md"]
                Codex["codex.md"]
            end

            Common --> PerHarness
            Rules --> PerHarness
        end

        SkillMD -.lazy load.-> Patterns
        SkillMD -.lazy load.-> Mermaid
        SkillMD -.lazy load.-> Worked
        SkillMD -.lazy load.-> Common
    end

    Persona -.invokes when designing.-> SkillMD
Loading

Persona stays small and durable. Skill loads assets on demand. Per-harness adapters fan out under a stable substrate so adding a new harness is one file (open-closed).

The 7-step design discipline

flowchart LR
    S1[1. Capture<br/>intent] --> S2[2. Component<br/>diagram]
    S2 --> S3[3. Thread/<br/>sequence dgm]
    S3 --> S4[4. SoC<br/>review]
    S4 --> S5[5. Compliance<br/>check]
    S5 --> S6[6. Handoff<br/>packet]
    S6 --> S7[7. Caller:<br/>portability + draft + validate]

    S2 -.loads.-> Patterns[architecture-patterns.md]
    S3 -.loads.-> Mermaid[mermaid-conventions.md]
    S5 -.loads.-> Common[runtime-affordances/common.md]
    S7 -.loads.-> Adapters[per-harness/*.md]

    classDef arch fill:#ddf,stroke:#009
    classDef code fill:#dfd,stroke:#090
    class S1,S2,S3,S4,S5,S6 arch
    class S7 code
Loading

Architect stays in the diagram + substrate world. The "coder" step pulls in harness-specific adapters only when generating actual primitive files. This mirrors python-architect -> python-architecture -> coder.

Worked example: re-architecting apm-review-panel

Today (P1 single-loop):

sequenceDiagram
    participant Caller
    participant Panel as apm-review-panel<br/>(single thread, persona swaps)
    Caller->>Panel: review this PR
    Panel->>Panel: think as Architect
    Panel->>Panel: think as DevX
    Panel->>Panel: think as Security
    Panel->>Panel: think as CLI
    Panel->>Panel: think as CEO
    Panel->>Panel: think as Growth
    Panel->>Caller: synthesized verdict
    Note over Panel: One context window,<br/>attention degrades by lens 4-5
Loading

Proposed (P2 fan-out + synthesizer):

sequenceDiagram
    participant Caller
    participant CEO as Parent (CEO orchestrator)
    participant A as spawn(Architect)
    participant D as spawn(DevX)
    participant S as spawn(Security)
    participant C as spawn(CLI)
    participant G as spawn(Growth)
    Caller->>CEO: review this PR
    par fan-out
        CEO->>A: review (fresh context)
        CEO->>D: review (fresh context)
        CEO->>S: review (fresh context)
        CEO->>C: review (fresh context)
        CEO->>G: review (fresh context)
    end
    A-->>CEO: finding set
    D-->>CEO: finding set
    S-->>CEO: finding set
    C-->>CEO: finding set
    G-->>CEO: finding set
    CEO->>CEO: arbitrate, synthesize
    CEO->>Caller: verdict
Loading

Each lens gets a fresh context window with its own persona file and only the artifacts it needs. The CEO is the parent thread, holds orchestration, arbitrates conflicts. (This PR documents the pattern; actually rewriting apm-review-panel is a follow-up that dogfoods the new skill.)


How

Files added/changed

File Status Purpose
.apm/agents/apm-primitives-architect.agent.md rewritten Durable persona: runtime stack, persona/thread disambiguation, principles, anti-patterns. No harness syntax.
.apm/skills/apm-primitives-architecture/SKILL.md new 7-step design discipline entrypoint
.apm/skills/apm-primitives-architecture/assets/architecture-patterns.md new P1 single-loop, P2 fan-out+synthesizer, P3 conditional dispatch, P4 validation gate, P5 supervisor/worker, P6 orchestrator+persisted artifact, with selection heuristic
.apm/skills/apm-primitives-architecture/assets/mermaid-conventions.md new Diagram-per-step mapping; GitHub render gotchas (e.g. classDiagram :::cssClass shorthand limitation)
.apm/skills/apm-primitives-architecture/assets/worked-example-review-panel.md new Canonical fan-out reference; before/after analysis
.apm/skills/apm-primitives-architecture/assets/runtime-affordances/common.md new Substrate: PERSONA, SKILL, RULE, SPAWN, ORCHESTRATOR
.apm/skills/apm-primitives-architecture/assets/runtime-affordances/portability-rules.md new Declaration requirement + open-closed for harnesses
.apm/skills/apm-primitives-architecture/assets/runtime-affordances/per-harness/copilot.md new Copilot CLI mapping
.apm/skills/apm-primitives-architecture/assets/runtime-affordances/per-harness/claude-code.md new Claude Code mapping
.apm/skills/apm-primitives-architecture/assets/runtime-affordances/per-harness/cursor.md new Cursor mapping
.apm/skills/apm-primitives-architecture/assets/runtime-affordances/per-harness/opencode.md new OpenCode mapping
.apm/skills/apm-primitives-architecture/assets/runtime-affordances/per-harness/codex.md new Codex CLI mapping

How adapters were authored

5 explore subagents fanned out in parallel (dogfooding the very pattern this PR proposes). Each got: common.md substrate, pointer to APM's src/apm_cli/adapters/client/<harness>.py + integration/targets.py for ground truth, official doc URLs, and instructions to mark TODO: official docs needed rather than invent.

TODO markers reported by adapter subagents

These are gaps where official docs are not yet public — flagging for follow-up:

  • copilot.md: agent spawning syntax (Task tool); trigger orchestrator (workflows). Public docs incomplete.
  • cursor.md: subagent parallelism semantics (sequential vs parallel unclear); hook trigger types not fully exposed.
  • opencode.md: scope-attached rule files (no glob-based scoping feature exists in OpenCode).
  • claude-code.md: 0 TODOs. All 5 substrate concepts mapped to live docs.
  • codex.md: 0 TODOs. Codex deliberately lacks first-class spawn/orchestrator; documented with workarounds.

Constraints respected

  • ASCII-only (U+0020-U+007E). Verified with LC_ALL=C grep — clean.
  • .apm/ is the source of truth; .github/{skills,agents,instructions}/ regenerated by apm install --target copilot (not touched here).
  • Each asset file < 200 lines; SKILL.md loads them on demand.
  • No .cursor/, .claude/, etc. files added — those belong to compiled output.


Update: composition layer (second commit 3c6a0df9)

The first round redesigned the architect for runtime affordances (how harnesses spawn threads, load skills, etc.). A second durable concern surfaced: APM itself is the composition substrate for primitives -- skills depend on agents, agents depend on instructions, packages bundle them, and the dependency tree is infinite. The architect was blind to this.

Same lesson, applied a second time: separate the durable concept from today's tool.

What was added

  • Persona truth Add ARM64 Linux support to CI/CD pipeline #4: COMPOSITION IS FIRST-CLASS -- a primitive can itself be a MODULE with its own dependencies. PRIMITIVE-vs-MODULE disambiguation block added next to the existing PERSONA-vs-SUBAGENT one.
  • Step 3.5 in the design discipline -- per-box composition decision (INLINE / LOCAL SIBLING / EXTERNAL MODULE) with a dependency-graph diagram in the handoff packet.
  • assets/composition-substrate.md (NEW, 140 lines) -- 6 named mechanisms: MODULE, DEPENDENCY, DISTRIBUTION BOUNDARY, TRANSITIVE CLOSURE, VERSION PINNING, PORTABILITY MODE. Anti-patterns: DUPLICATED LEAF, HIDDEN EXTERNAL, UNPINNED CRITICAL DEP, TRANSITIVE BLOAT, BOUNDARY VIOLATION, TOOL LEAK. Promotion rule (rule of three / independent cadence / different owner / pinning-worthy).
  • assets/module-system-adapters/apm.md (NEW, 60 lines) -- a thin pointer that delegates to the existing apm-usage skill at packages/apm-guide/.apm/skills/apm-usage/. Loaded only at coder step 7b, only when the design declared external modules.
  • P7 in architecture-patterns.md -- composed-module pattern (depend, don't duplicate).
  • mermaid-conventions.md -- dependency-graph diagram type for step 3.5.

The mental model

flowchart TB
    subgraph Durable["DURABLE LAYER (architect persona + substrate)"]
        Truths[4 truths<br/>incl. COMPOSITION IS FIRST-CLASS]
        RtSub[runtime-affordances/common.md<br/>5 named mechanisms]
        CompSub[composition-substrate.md<br/>6 named mechanisms]
    end

    subgraph Adapters["ADAPTER LAYER (today's tools, swap freely)"]
        Harness[per-harness/copilot.md<br/>per-harness/claude-code.md<br/>per-harness/cursor.md<br/>per-harness/opencode.md<br/>per-harness/codex.md]
        ModSys[module-system-adapters/apm.md<br/>--&gt; delegates to apm-usage skill]
    end

    subgraph Tool["TOOL KNOWLEDGE (lives elsewhere, depend don't duplicate)"]
        ApmUsage[apm-usage skill<br/>apm.yml schema, CLI, lockfile,<br/>8 dep types, hybrid mode]
    end

    Truths --> RtSub
    Truths --> CompSub
    RtSub -.coder loads at 7b.-> Harness
    CompSub -.coder loads at 7b.-> ModSys
    ModSys -.points at.-> ApmUsage

    classDef durable fill:#dfd,stroke:#090
    classDef adapter fill:#ffd,stroke:#990
    classDef tool fill:#ddf,stroke:#009
    class Truths,RtSub,CompSub durable
    class Harness,ModSys adapter
    class ApmUsage tool
Loading

The architect now reasons in MODULE / DEPENDENCY / DISTRIBUTION BOUNDARY. It never sees apm.yml. APM-specific syntax (CLI, manifest, lockfile, hybrid mode) lives exclusively in apm-usage and is consulted only at the coder step. A future module-system tool ships as a sibling adapter file -- zero edits to substrate or persona.

Dogfooding

The adapter is the canonical example of the principle it teaches:

module-system-adapters/apm.md  =  60 lines pointing at apm-usage
                            (NOT  600 lines re-documenting APM)

This is DEPEND, DON'T DUPLICATE (composition-substrate.md anti-pattern DUPLICATED LEAF) applied to the architect's own asset bundle. If apm-usage evolves, the adapter doesn't drift -- it just points.

Updated process diagram

flowchart LR
    S1[1. Intent] --> S2[2. Decompose]
    S2 --> S3[3. Runtime fit]
    S3 --> S35[3.5 Composition<br/>NEW]
    S35 --> S4[4. SoC + boundaries]
    S4 --> S5[5. Anti-patterns]
    S5 --> S6[6. Handoff packet]
    S6 --> S7a[7a. Critique]
    S7a --> S7b[7b. Code<br/>loads adapters per box]
    S7b --> S8[8. Verify]

    classDef new fill:#ffd,stroke:#990,stroke-width:2px
    class S35 new
Loading

Files in second commit

File Status Why
.apm/agents/apm-primitives-architect.agent.md modified +truth #4, +PRIMITIVE/MODULE disambig, +adapter ignorance
.apm/skills/apm-primitives-architecture/SKILL.md modified +step 3.5, +handoff packet items, +adapter loading at 7b
assets/composition-substrate.md new 6 durable mechanisms + anti-patterns + promotion rule
assets/module-system-adapters/apm.md new thin pointer to apm-usage skill
assets/architecture-patterns.md modified P7 composed-module pattern
assets/mermaid-conventions.md modified dependency-graph diagram type


Update: plan persistence layer (third commit 1d4be965)

The redesign so far gave the architect runtime affordances and composition. A third durable concern surfaced: LLMs forget. Attention decays with distance from the focus point — every long session silently drops earlier decisions, todos, and constraints. The architect was implicitly relying on whatever harness it ran in to provide a plan store, without naming the affordance or telling the executor to use it.

Same pattern, applied a third time: separate the durable cope from today's tool.

What was added

  • Persona truth apm install <my-apm-package-repo> #5: PLAN BEFORE EXECUTION — non-trivial work emits a plan artifact before any module body is drafted; the plan persists outside the context window so the executor can reground itself. Truth Why do we need a GitHub token? #1 was extended with the explicit corollary that long-distance state belongs in a persistence slot, not in the prompt.
  • Substrate concept 6 in runtime-affordances/common.md: PLAN PERSISTENCE — names the underlying property (ATTENTION DEGRADATION) and the four slots every modern harness offers (PLAN ARTIFACT, TODO/STATUS, optional CHECKPOINT, optional FILES). Specifies write-once-early and reload-at-re-grounding behavior.
  • Pattern P8 in architecture-patterns.md: Plan-first with persisted plan — declared explicitly ORTHOGONAL to P1-P7. Combine P8 with whichever topology fits. Includes ASCII sketch of the persist/reload loop, the WHEN clause, the INTERLOCK requirement (without reload, persistence is dead weight), and anti-patterns (post-hoc plan, write-once-never-reload, stuffing the whole plan into every spawn).
  • SKILL.md step 6 retitled to handoff packet (this IS the plan; persist it) — the packet is what gets persisted to the runtime store before step 7b begins. Step 7b instructs the executor to RELOAD before each module / spawn / failure-recovery. Process diagram updated to show PERSIST at the 6→7b boundary and RELOAD inside 7b.
  • Per-harness adapters: section 6 in all 5 files:
    • copilot.md~/.copilot/session-state/<id>/plan.md + checkpoints/ + files/ + per-session SQLite todos/todo_deps tables via the sql tool (the harness this very PR was written in).
    • claude-code.md — TodoWrite tool with file-based fallback for cross-session plans.
    • cursor.md, opencode.md, codex.md — honest TODO: official docs needed markers + the substrate-portable fallback (plan.md in workspace, re-read at re-grounding points). User can fill in once docs land.

The mental model (now three durable layers, three adapter slots)

flowchart TB
    subgraph DurableConcerns["DURABLE CONCERNS (named in persona truths)"]
        T1[Truth 1<br/>context finite + attention decay]
        T2[Truth 2<br/>context explicit]
        T3[Truth 3<br/>output probabilistic]
        T4[Truth 4<br/>composition first-class]
        T5[Truth 5<br/>plan before execution<br/>NEW]
    end

    subgraph DurableSubstrate["DURABLE SUBSTRATE (load at design time)"]
        RA[runtime-affordances/common.md<br/>6 named mechanisms<br/>incl. PLAN PERSISTENCE]
        CS[composition-substrate.md<br/>6 named mechanisms]
        AP[architecture-patterns.md<br/>P1..P7 topologies<br/>P8 plan-first ORTHOGONAL]
    end

    subgraph Adapters["ADAPTER LAYER (load only at coder step)"]
        H[per-harness/<br/>copilot|claude|cursor|<br/>opencode|codex .md<br/>each maps all 6 substrate concepts]
        M[module-system-adapters/apm.md<br/>delegates to apm-usage skill]
    end

    T1 --> RA
    T5 --> RA
    T5 --> AP
    T4 --> CS
    RA -.7b.-> H
    CS -.7b.-> M

    classDef durable fill:#dfd,stroke:#090
    classDef adapter fill:#ffd,stroke:#990
    classDef new fill:#ffe680,stroke:#990,stroke-width:2px
    class T1,T2,T3,T4,RA,CS,AP durable
    class T5 new
    class H,M adapter
Loading

The persist/reload cycle (P8)

sequenceDiagram
    participant A as Architect (steps 1-6)
    participant P as Plan store<br/>(harness-provided)
    participant C as Coder thread (step 7b)
    participant W as Worker subagent (optional)

    A->>A: design (steps 1-3.5-4-5)
    A->>P: PERSIST handoff packet (step 6)
    Note over A,P: Truth #5: plan before execution
    A--xC: design ends; coder takes over

    C->>P: RELOAD plan
    C->>C: draft module 1
    C->>P: update todo: module-1 done

    C->>P: RELOAD plan
    C->>W: spawn with task = pointer to plan slice
    Note over C,W: child gets POINTER, not full plan
    W-->>C: return result
    C->>P: RELOAD plan (verify state still matches)
    C->>P: update todos

    C->>C: validate (step 8)
    C->>P: final status
Loading

Files changed in third commit

File Status Why
.apm/agents/apm-primitives-architect.agent.md modified +truth #5; truth #1 extended with attention-decay corollary; "five truths" labels updated
assets/runtime-affordances/common.md modified +substrate concept 6 PLAN PERSISTENCE; +invariant on attention decay; counts updated to "six concepts"
assets/architecture-patterns.md modified +P8 plan-first (orthogonal); selection-heuristic note on orthogonality
.apm/skills/apm-primitives-architecture/SKILL.md modified step 6 PERSIST; step 7b RELOAD; process diagram updated
assets/runtime-affordances/per-harness/copilot.md modified +section 6: session-state + SQL todos
assets/runtime-affordances/per-harness/claude-code.md modified +section 6: TodoWrite + file fallback
assets/runtime-affordances/per-harness/cursor.md modified +section 6: TODO + portable fallback
assets/runtime-affordances/per-harness/opencode.md modified +section 6: TODO + portable fallback
assets/runtime-affordances/per-harness/codex.md modified +section 6: portable fallback (Codex is intentionally minimal)

Recursive proof (dogfood)

This entire PR was built across multiple turns in GitHub Copilot CLI using ~/.copilot/session-state/<id>/plan.md + checkpoints/ + the sql tool's todos/todo_deps tables. The architect was free-riding on PLAN PERSISTENCE without acknowledging it. Truth #5 + substrate concept 6 + P8 codify what was already happening, so the next architect session — in any harness — can do it deliberately.


Trade-offs

Choice Why Cost
Split persona + skill (vs one big agent.md) Persona stays under load budget; skill assets lazy-load Two-file mental model, but mirrors python-architect/python-architecture
Layered runtime affordances (common + per-harness) Open-closed for new harnesses; durable mental model survives harness churn Slightly more files; readers must follow common.md -> per-harness/.md
Worked example does NOT actually edit apm-review-panel This PR ships the discipline; a separate PR dogfoods it cleanly apm-review-panel keeps shipping single-loop until follow-up lands
TODO markers preserved Honest about doc gaps; lets future contributors fill in Some adapters incomplete until official docs land

How to test

  1. Open .apm/agents/apm-primitives-architect.agent.md and verify it carries no harness syntax (no mentions of .cursor/, .claude/, etc.). It should read as durable principles.
  2. Open .apm/skills/apm-primitives-architecture/SKILL.md and verify the 7-step process is present and assets are referenced lazily.
  3. Spot-check that assets/runtime-affordances/per-harness/ contains exactly 5 files.
  4. (Optional) Try the discipline: pick any existing primitive (e.g. apm-triage-panel) and walk it through the 7 steps to see whether the architecture holds up.

Unit tests: uv run pytest tests/unit tests/test_console.py -x — doc-only PR, no Python touched. Pre-existing failure on test_global_mcp_scope.py confirmed unrelated (also fails on main).

Co-authored-by: Copilot 223556219+Copilot@users.noreply.github.com

…time-affordance layering

Replaces the style/lint persona with a durable architectural mental model
plus a new apm-primitives-architecture skill that drives a 7-step design
discipline: intent -> component diagram -> thread/sequence diagram -> SoC
review -> compliance check -> handoff packet.

Key shifts:
- Persona disambiguates persona-scoping (text loaded into a thread to bias
  inference) from subagent (runtime-spawned child thread with fresh context
  window). Conflating these is the central error in agentic design.
- Architecture patterns catalog (P1-P6) with selection heuristic: >=3
  independent lenses with no shared state -> fan-out + parent synthesizer.
- Runtime-affordances split into common substrate + per-harness adapters
  (copilot, claude-code, cursor, opencode, codex). Adding a harness = drop
  one file in per-harness/, no other edits (open-closed).
- Worked example re-architects apm-review-panel from single-loop to
  fan-out + synthesizer to demonstrate the discipline.

Files for LLMs to execute, not humans to read; assets load on demand to
respect SKILL.md token budget.

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Copilot AI review requested due to automatic review settings April 25, 2026 15:39
Copy link
Copy Markdown
Contributor

Copilot AI left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Redesigns the apm-primitives-architect primitive from a style/lint-focused auditor into a durable architecture persona, and introduces a new apm-primitives-architecture skill that drives a structured, diagram-first design discipline with runtime-affordance layering across harnesses.

Changes:

  • Rewrites .apm/agents/apm-primitives-architect.agent.md to focus on durable runtime mental models, threading semantics, and diagram-first design discipline.
  • Adds .apm/skills/apm-primitives-architecture/ with a 7-step design process and modular assets (patterns catalog, Mermaid conventions, worked example).
  • Introduces a runtime-affordances substrate (common.md) plus portability rules and per-harness adapters (Copilot, Claude Code, Cursor, OpenCode, Codex).
Show a summary per file
File Description
.apm/agents/apm-primitives-architect.agent.md Replaces the previous architect guidance with durable runtime + threading design discipline and artifact-first outputs.
.apm/skills/apm-primitives-architecture/SKILL.md New entrypoint skill encoding the stepwise architecture process and lazy-loading of supporting assets.
.apm/skills/apm-primitives-architecture/assets/architecture-patterns.md Adds a topology catalog (P1–P6) to drive consistent orchestration shape selection.
.apm/skills/apm-primitives-architecture/assets/mermaid-conventions.md Defines diagram conventions + GitHub Mermaid rendering gotchas for reliable artifacts.
.apm/skills/apm-primitives-architecture/assets/worked-example-review-panel.md Provides a canonical before/after example for refactoring multi-lens panels into fan-out + synthesizer.
.apm/skills/apm-primitives-architecture/assets/runtime-affordances/common.md Defines the harness-agnostic substrate concepts used for portability-first designs.
.apm/skills/apm-primitives-architecture/assets/runtime-affordances/portability-rules.md Adds rules for when/how to justify per-harness reach beyond the substrate.
.apm/skills/apm-primitives-architecture/assets/runtime-affordances/per-harness/copilot.md Documents Copilot mapping for substrate concepts (with TODOs for missing public docs).
.apm/skills/apm-primitives-architecture/assets/runtime-affordances/per-harness/claude-code.md Documents Claude Code mapping for substrate concepts with doc citations.
.apm/skills/apm-primitives-architecture/assets/runtime-affordances/per-harness/cursor.md Documents Cursor mapping for substrate concepts (currently misaligned with repo integration paths).
.apm/skills/apm-primitives-architecture/assets/runtime-affordances/per-harness/opencode.md Documents OpenCode mapping for substrate concepts (includes citations to missing snapshot files).
.apm/skills/apm-primitives-architecture/assets/runtime-affordances/per-harness/codex.md Documents Codex mapping for substrate concepts (currently misaligned with repo integration paths/defaults).

Copilot's findings

Comments suppressed due to low confidence (1)

.apm/skills/apm-primitives-architecture/assets/worked-example-review-panel.md:95

  • Same issue for the sequenceDiagram block: it is not fenced as Mermaid, so it will render as plain text on GitHub. Update the fence to a Mermaid code block so the diagram is actually viewable.

sequenceDiagram
participant Orchestrator
participant LensA as Architect
participant LensB as LoggingUX
participant LensC as DevXUX
participant LensD as Security
participant LensE as Growth
participant Auth as Auth (cond)
participant Arbiter
Orchestrator->>LensA: spawn(load Architect persona, scope=PR)
Orchestrator->>LensB: spawn(load LoggingUX persona, scope=PR)
Orchestrator->>LensC: spawn(load DevXUX persona, scope=PR)
Orchestrator->>LensD: spawn(load Security persona, scope=PR)
Orchestrator->>LensE: spawn(load Growth persona, scope=PR)
alt conditional fires
Orchestrator->>Auth: spawn(load Auth persona, scope=PR)
Auth-->>Orchestrator: findings
end
LensA-->>Orchestrator: findings
LensB-->>Orchestrator: findings
LensC-->>Orchestrator: findings
LensD-->>Orchestrator: findings
LensE-->>Orchestrator: findings
Note over Orchestrator: completeness gate
Orchestrator->>Arbiter: spawn(load Arbiter persona, plus all findings as input)
Arbiter-->>Orchestrator: synthesized verdict
Note over Orchestrator: single-writer interlock on output sink

  • Files reviewed: 12/12 changed files
  • Comments generated: 11

Comment on lines +12 to +23
## 1. PERSONA SCOPING FILE

In Cursor: Project Rule with frontmatter, or AGENTS.md (legacy).
- File extension: .mdc (recommended) or .md (legacy AGENTS.md)
- Folder: .cursor/rules/ (project), AGENTS.md in root (legacy)
- Frontmatter fields: description, globs, alwaysApply
- Activation: Rules are loaded when alwaysApply=true (always) or
when Agent determines relevance based on description. AGENTS.md
is automatically loaded as project-level instructions.
- Notes: alwaysApply=false means Cursor Agent decides relevance.
Nested AGENTS.md files are supported in subdirectories.
- Source: https://docs.cursor.com/context/rules
Copy link

Copilot AI Apr 25, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This section says Cursor persona scoping is done via rules (.cursor/rules/*.mdc) or AGENTS.md, but APM's Cursor target mapping treats persona scoping as an agent primitive deployed to .cursor/agents/*.md (separate from rules/instructions). Align this adapter to the repo's actual integration paths so designers don't conflate rules vs agents.

Copilot uses AI. Check for mistakes.
Comment on lines +29 to +34
- Closest equivalent: .agents/skills/ directory containing SKILL.md + assets/
- Standard body fields: name, description, steps with asset references
- Assets folder: .agents/skills/<skill-name>/assets/
- Activation: Agents select skills matching task description
- Notes: Cursor implements agentskills.io SKILL.md container and discovery;
assets load on demand as agents execute steps.
Copy link

Copilot AI Apr 25, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The skill deployment path here doesn't match APM's Cursor integration. In this repo, Cursor skills deploy under .cursor/skills/<name>/SKILL.md (not .agents/skills/). Using the wrong path in the adapter will cause incorrect portability decisions and incorrect emitted files.

Suggested change
- Closest equivalent: .agents/skills/ directory containing SKILL.md + assets/
- Standard body fields: name, description, steps with asset references
- Assets folder: .agents/skills/<skill-name>/assets/
- Activation: Agents select skills matching task description
- Notes: Cursor implements agentskills.io SKILL.md container and discovery;
assets load on demand as agents execute steps.
- Closest equivalent: .cursor/skills/<skill-name>/ directory containing SKILL.md + assets/
- Standard body fields: name, description, steps with asset references
- Assets folder: .cursor/skills/<skill-name>/assets/
- Activation: Agents select skills matching task description
- Notes: Cursor discovers SKILL.md-based skill containers under
.cursor/skills/; assets load on demand as agents execute steps.

Copilot uses AI. Check for mistakes.
Comment on lines +66 to +72
In Cursor: Hooks (.cursor/hooks/*.json) for event-driven actions.
- Mechanism: JSON hook configuration in .cursor/hooks/ directory.
Each hook file specifies trigger event and associated action.
- Trigger types: TODO: official docs needed (repository events,
schedule, user invocation presumed).
- Scope: Repo-local; not yet integrated with global ~/.cursor/ scope.
- Notes: Hook semantics not fully documented in official API.
Copy link

Copilot AI Apr 25, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Cursor hooks are integrated by APM into a merged .cursor/hooks.json (plus per-package scripts under .cursor/hooks/<pkg>/), not individual .cursor/hooks/*.json files. Documenting the wrong hook shape will lead to non-functional orchestrator designs.

Suggested change
In Cursor: Hooks (.cursor/hooks/*.json) for event-driven actions.
- Mechanism: JSON hook configuration in .cursor/hooks/ directory.
Each hook file specifies trigger event and associated action.
- Trigger types: TODO: official docs needed (repository events,
schedule, user invocation presumed).
- Scope: Repo-local; not yet integrated with global ~/.cursor/ scope.
- Notes: Hook semantics not fully documented in official API.
In Cursor via APM: merged hook config at .cursor/hooks.json, with
package-owned scripts under .cursor/hooks/<pkg>/ for event-driven
actions.
- Mechanism: APM merges hook declarations into a single
.cursor/hooks.json file. Per-package hook scripts and helper files
live under .cursor/hooks/<pkg>/.
- Trigger types: TODO: confirm exact Cursor hook event names from
official docs before depending on specific triggers.
- Scope: Repo-local project configuration emitted by APM.
- Notes: Do not model hooks as individual .cursor/hooks/*.json files;
that shape does not match APM's Cursor integration contract.

Copilot uses AI. Check for mistakes.
Comment on lines +7 to +12
Official docs cited:
- https://github.com/anomalyco/opencode
- Playwright MCP snapshot: .playwright-mcp/opencode-agents.md
- Playwright MCP snapshot: .playwright-mcp/opencode-commands.md
- Playwright MCP snapshot: .playwright-mcp/opencode-config.md

Copy link

Copilot AI Apr 25, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This adapter cites Playwright snapshot files under .playwright-mcp/ (e.g., .playwright-mcp/opencode-agents.md), but those snapshot files are not present in the repository. Either add the referenced snapshot artifacts (if intended) or remove/replace these citations with sources that exist (official docs, or the relevant APM integration code).

Copilot uses AI. Check for mistakes.
Comment on lines +5 to +10
every concept here has an equivalent in every supported harness,
even if the file name, folder location, or trigger field differs.

The architect persona designs against THIS file. Per-harness
adapters in `per-harness/` map the substrate to specific syntax;
load them only when a primitive must reach beyond the substrate.
Copy link

Copilot AI Apr 25, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This section says every concept in the common substrate has an equivalent in every supported harness, but the per-harness adapters in this PR describe some targets as lacking PERSONA SCOPING FILE / CHILD-THREAD SPAWN / TRIGGER ORCHESTRATOR (e.g., Codex). That contradiction makes the substrate ambiguous for the skill's step 7 portability check; either soften the claim (e.g., allow 'native OR external/orchestrated equivalent') or align the adapters to map each substrate concept to a concrete mechanism/workaround per target.

Suggested change
every concept here has an equivalent in every supported harness,
even if the file name, folder location, or trigger field differs.
The architect persona designs against THIS file. Per-harness
adapters in `per-harness/` map the substrate to specific syntax;
load them only when a primitive must reach beyond the substrate.
every concept here must map in every supported harness to either a
native mechanism or a documented external/orchestrated equivalent,
even if the file name, folder location, trigger field, or execution
path differs.
The architect persona designs against THIS file. Per-harness
adapters in `per-harness/` must map each substrate concept to the
concrete native mechanism or workaround for that target; load them
only when a primitive must reach beyond the substrate.

Copilot uses AI. Check for mistakes.
Comment on lines +87 to +88
- GitHub Models Integration: Codex CLI auto-configures free access to
GitHub Models (gpt-4o-mini) via GITHUB_TOKEN; no OpenAI key required.
Copy link

Copilot AI Apr 25, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The Codex runtime details here don't match the repo's own Codex setup defaults. scripts/runtime/setup-codex.sh configures Codex for GitHub Models with model = "openai/gpt-4o", but this adapter claims a specific default of gpt-4o-mini. Please either update to the repo's actual default model, or avoid naming a specific model unless it's sourced from current APM configuration/docs.

Suggested change
- GitHub Models Integration: Codex CLI auto-configures free access to
GitHub Models (gpt-4o-mini) via GITHUB_TOKEN; no OpenAI key required.
- GitHub Models Integration: Codex CLI can be configured to use
GitHub Models via GITHUB_TOKEN; no OpenAI key required.

Copilot uses AI. Check for mistakes.
Comment on lines +90 to +91
Each diagram block in the handoff packet sits between fenced
``` ```mermaid ``` ``` markers. The handoff packet is markdown;
Copy link

Copilot AI Apr 25, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This paragraph about Mermaid fencing is likely to render incorrectly (it contains nested triple-backtick sequences like ``` ```mermaid ``` ```). Consider rephrasing it to literally say "use a fenced code block with language 'mermaid'" (or show a single, valid example) so readers/LLMs don't copy a malformed fence.

Suggested change
Each diagram block in the handoff packet sits between fenced
``` ```mermaid ``` ``` markers. The handoff packet is markdown;
Each diagram block in the handoff packet must use a fenced code
block with language `mermaid`. The handoff packet is markdown;

Copilot uses AI. Check for mistakes.
Comment on lines +16 to +24
A markdown file (with frontmatter) loaded as text into a thread at
the start of execution to bias inference toward a specific lens or
role. It does NOT execute. It does NOT spawn anything. It is a
prompt-shaped knowledge artifact.

Substrate fields (every harness offers these or equivalents):
- a unique `name`
- a `description` (plain text the harness shows to the user / model)
- the body: instructions, principles, anti-patterns
Copy link

Copilot AI Apr 25, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The substrate definition for PERSONA SCOPING FILE assumes a Markdown + frontmatter format, but APM's own Codex integration emits agents as .toml (see targets.py). If the substrate is meant to be truly harness-agnostic, consider defining this concept as a 'structured persona config file' rather than specifically Markdown, and let per-harness adapters specify the concrete format.

Suggested change
A markdown file (with frontmatter) loaded as text into a thread at
the start of execution to bias inference toward a specific lens or
role. It does NOT execute. It does NOT spawn anything. It is a
prompt-shaped knowledge artifact.
Substrate fields (every harness offers these or equivalents):
- a unique `name`
- a `description` (plain text the harness shows to the user / model)
- the body: instructions, principles, anti-patterns
A structured persona config file loaded as text into a thread at
the start of execution to bias inference toward a specific lens or
role. It does NOT execute. It does NOT spawn anything. It is a
prompt-shaped knowledge artifact. The concrete file format is
adapter-defined per harness, for example Markdown plus frontmatter
or TOML.
Substrate fields (every harness offers these or equivalents):
- a unique `name`
- a `description` (plain text the harness shows to the user / model)
- persona content: instructions, principles, anti-patterns

Copilot uses AI. Check for mistakes.
Comment on lines +43 to +62
```
flowchart LR
O{Panel orchestrator}
P((Architect))
L((Logging UX))
U((DevX UX))
Sec((Security))
G((Growth))
Auth((Auth))
A((Arbiter))
O --> P
O --> L
O --> U
O --> Sec
O --> G
O -. conditional .-> Auth
O --> A
classDef new stroke-dasharray: 5 5;
class A new;
```
Copy link

Copilot AI Apr 25, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The flowchart and sequenceDiagram blocks are fenced as plain code blocks, so GitHub will not render them as Mermaid. Since this file is meant to be executed/used as the canonical reference shape, the diagram fences should be tagged with mermaid (and aligned with assets/mermaid-conventions.md).

This issue also appears on line 67 of the same file.

Copilot uses AI. Check for mistakes.
Comment on lines +120 to +129
## Compliance summary

| Check | Old design | New design |
|---|---|---|
| Reduced Scope (per-lens fresh window) | FAIL | PASS |
| Orchestrated Composition (independent contracts) | FAIL | PASS |
| Single-writer interlock on output | PASS | PASS |
| God module avoidance | FAIL (one thread = many lenses) | PASS |
| Fan-out where applicable | FAIL | PASS |

Copy link

Copilot AI Apr 25, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The markdown table in the compliance summary uses || at the start of each row, which renders as an extra empty column in GitHub-flavored Markdown. Use single leading pipes (|) for a 3-column table so it renders correctly.

Copilot uses AI. Check for mistakes.
… layer)

Extends the architect with a 4th durable truth (COMPOSITION IS
FIRST-CLASS) and the PRIMITIVE-vs-MODULE disambiguation. Adds a new
step 3.5 to the design discipline (composition decision: inline /
local sibling / external module) plus a dependency-graph diagram.

Mirrors the runtime-affordances layering: substrate
(composition-substrate.md, 6 named mechanisms: MODULE, DEPENDENCY,
DISTRIBUTION BOUNDARY, TRANSITIVE CLOSURE, VERSION PINNING,
PORTABILITY MODE) + adapter (module-system-adapters/apm.md, a thin
pointer that delegates to the existing apm-usage skill).

The architect persona stays ignorant of today's tool: no apm.yml,
no CLI commands, no lockfile syntax. APM-specific knowledge lives
exclusively in apm-usage and is loaded only at the coder step,
only when the design declared external modules. Open-closed: a
future module-system tool is added by dropping a sibling adapter,
no edits to the substrate or the persona.

This is the canonical 'depend, don't duplicate' example: the
adapter is 60 lines that point at apm-usage rather than 600 lines
re-documenting APM.

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
@danielmeppiel
Copy link
Copy Markdown
Collaborator Author

Follow-up commit: composition substrate + module-system adapter

Applied the lesson the skill itself teaches: separate durable concepts from today's tool.

What changed

  • Persona: 4th durable truth (COMPOSITION IS FIRST-CLASS) + PRIMITIVE-vs-MODULE disambiguation.
  • SKILL.md: new step 3.5 composition decision (per-box: inline / local sibling / external module) + step 7b loads module-system adapter only when external modules were declared.
  • New: assets/composition-substrate.md -- 6 named mechanisms (MODULE, DEPENDENCY, DISTRIBUTION BOUNDARY, TRANSITIVE CLOSURE, VERSION PINNING, PORTABILITY MODE). No apm.yml, no CLI, no lockfile syntax. Pure substrate.
  • New: assets/module-system-adapters/apm.md -- 60-line pointer that delegates to the existing apm-usage skill at packages/apm-guide/.apm/skills/apm-usage/. Mirrors runtime-affordances/per-harness/<x>.md shape.
  • architecture-patterns.md: P7 composed-module pattern + promotion rule (rule of three / independent cadence / different owner / pinning-worthy).
  • mermaid-conventions.md: dependency-graph diagram type added at step 3.5.

Mental model

DURABLE (lives in architect)              EPHEMERAL (lives in apm-usage)
============================              ============================
MODULE / DEPENDENCY / etc.                apm.yml schema, CLI, lockfile
"depend, don't duplicate"                 hybrid mode, plugin export
distribution boundary                      8 dependency types

The architect now reasons about module graphs without knowing what tool resolves them. APM is just today's instance; apm-usage is the single source of truth for its syntax.

This is the canonical 'depend, don't duplicate' example -- the adapter is 60 lines that point at apm-usage rather than 600 lines re-documenting APM.

Names ATTENTION DEGRADATION explicitly (truth #1 corollary) and
adds PLAN BEFORE EXECUTION as the 5th durable truth. The architect
now treats plan persistence as a first-class runtime affordance
rather than a happy accident of the harness it runs in.

Substrate (depend, don't duplicate):
- runtime-affordances/common.md: 6th named concept PLAN PERSISTENCE
  with substrate slots PLAN ARTIFACT / TODO-STATUS / CHECKPOINT /
  FILES; substrate invariant added that long-distance state belongs
  outside the prompt.
- architecture-patterns.md: P8 Plan-first with persisted plan,
  declared ORTHOGONAL to P1-P7. Combine P8 with whichever topology
  fits. Selection-heuristic note explains the orthogonality.
- SKILL.md: step 6 retitled (handoff packet IS the plan; persist
  it). Step 7b instructs the executor to RELOAD the plan at
  re-grounding boundaries. Process diagram updated to show PERSIST
  at step 6 boundary and RELOAD at step 7b.

Adapters (depend, don't duplicate):
- per-harness/copilot.md: section 6 documents
  ~/.copilot/session-state/<id>/{plan.md,checkpoints/,files/} +
  per-session SQLite todos/todo_deps via the sql tool.
- per-harness/claude-code.md: section 6 documents the TodoWrite
  tool with file-based fallback for cross-session plans.
- per-harness/cursor.md, opencode.md, codex.md: section 6 with
  honest TODO markers + the substrate-portable fallback (plan.md
  in workspace, re-read at re-grounding points).

Recursive proof: this very session relies on plan.md +
checkpoints + SQL todos in Copilot CLI -- the architect was
silently free-riding on a runtime affordance it failed to
acknowledge. That is now codified.

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
@danielmeppiel
Copy link
Copy Markdown
Collaborator Author

Third commit shipped: plan persistence as durable cure for attention decay.

Same durable-vs-tool pattern, third instance:

  • truth apm install <my-apm-package-repo> #5 PLAN BEFORE EXECUTION (persona)
  • substrate concept 6 PLAN PERSISTENCE in runtime-affordances/common.md
  • pattern P8 plan-first (orthogonal to P1-P7)
  • step 6 PERSIST + step 7b RELOAD codified in SKILL.md
  • per-harness section 6 in all 5 adapters (Copilot well-documented, Claude TodoWrite + fallback, Cursor/OpenCode/Codex with honest TODOs + portable fallback)

Recursive proof: this PR was written using ~/.copilot/session-state/<id>/plan.md + SQL todos + checkpoints. The architect was free-riding on the affordance without acknowledging it; now codified so the next architect session in any harness can do it deliberately.

PR description updated with mermaid diagrams for the 3-layer model and the persist/reload sequence.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants