AI Coding Workflows & Skills: Compare Tools, Pick Right Combo
The article analyzes AI-assisted programming workflows, comparing tools like AGENTS.md, ADR, OpenSpec, Spec Kit, Superpowers, Matt Skills, and Ponytail, mapping each to specific project problems, and provides a selection guide for three project types with practical examples.
Recent discussions on AI programming skills highlight two popular tools: grill-me and Ponytail. One clarifies requirements before coding; the other prevents agents from over-implementing during coding. They solve different problems and should not be blindly added to every repository.
A repository-level AI programming workflow consists of standing rules, decision records, specification management, execution methods, and engineering gates. AGENTS.md, ADR, OpenSpec, Spec Kit, Superpowers, Matt Skills, and Ponytail each cover distinct responsibilities. Identify where your project loses control, then choose tools.
Problem-to-Tool Mapping
Agent keeps forgetting repository rules → AGENTS.md — Standing instructions and entry point for other references
Complex changes lose state across sessions → OpenSpec / Spec Kit — Specifications, plans, tasks, and progress
Agent often skips clarification, testing, or review → Superpowers / Matt Skills — Execution methods
Agent adds abstractions and compatibility layers on its own → Ponytail — Only the minimal implementation needed now (YAGNI)
Old solutions keep being re-proposed → ADR — Record technical decisions and their rationale
Errors must never happen → Types, tests, CI, permissions, runtime validation — Directly reject errors
These tools can be combined, but each piece of information should have a single source of truth.
AGENTS.md: Get the Repository Entry Right First
Official Function
OpenAI's official documentation describes a three-level loading rule. Global ~/.codex/AGENTS.md holds cross-repository habits. Repository root AGENTS.md holds the current project's scope, source of truth, permissions, and minimum validation. Subdirectory AGENTS.md or AGENTS.override.md holds only local differences for that module.
Codex loads from global, then walks from repository root to the current working directory. Rules closer to the current directory come later and can override earlier ones. Each directory prefers AGENTS.override.md; if absent, it reads AGENTS.md. Merged content defaults to a maximum of 32 KiB; longer files may be truncated.
OpenAI's course also recommends keeping files short; its own examples are under 100 lines. This is an empirical warning line, not a hard standard.
Practical Advice
Do not put project rules in the global file. The repository root file should retain only what every task must not forget: project map, truth entry, safety boundaries, minimum validation, and task routing. Directory-level files are created only when a local module truly differs.
Formatting, linting, and rules verifiable by tests belong in CI. Full PRDs, interface specs, architecture history, and operational steps go back to their respective documents. AGENTS.md tells the agent where to read, not to duplicate all content.
My Practice
Below is my actual two-level structure (sanitized):
~/.codex/└── AGENTS.md # Cross-repository habitsdxc/├── AGENTS.md # DxC scope, permissions, truth, validation└── docs/ ├── README.md # Current documentation index └── decisions/ # ADR: accepted architectural decisionsMy global file mainly keeps Chinese writing conventions, reader-facing boundaries, and temporary resource cleanup. The DxC root file is about 66 lines; Choral about 69 lines. Both route details to other documents.
DxC's current AGENTS.md already links an ADR, but the entry could be clearer. I would write the sanitized routing like this:
## Scope & Truth- Current design entry: `docs/README.md`- Accepted ADR directory: `docs/decisions/`- On conflict between code, docs, and ADR: stop, correct truth, then continue## Minimum Validation- Code changes: format, lint, types, relevant tests, `git diff --check`- External writes: confirm first; no blind retries when result unknownI did not create directory-level AGENTS.md in DxC or the cross-platform audio project Choral just to fill a three-level structure. No subdirectory currently needs to override root rules. When a service later requires independent commands or stricter permissions, rules will be placed in the directory closest to the code.
How to choose: Long-lived repositories should at least write a root AGENTS.md. Add a global file when you have stable cross-repository habits. Add directory-level files only when local rules genuinely differ.
ADR: Let the Agent Find the "Why"
Official Function
ADR stands for Architecture Decision Record. One ADR records a single important decision: the context at the time, alternatives considered, the final decision, and the consequences to accept.
ADR predates AI programming. Michael Nygard's classic 2011 structure already includes title, status, context, decision, and consequences. It has long existed in architecture practice but has not become a default repository file like README, tests, or CI.
Traditional teams sometimes recover decision rationale from meetings, tickets, and long-tenured engineers. Agents have not attended those discussions, and new sessions rebuild context from scratch. They can see "how it is done now" from code, but not "which alternatives were tried and why they were dropped."
In my practice, this is exactly why ADR is more valuable in AI programming:
Agents can quickly generate a locally reasonable solution, and even faster spread old mistakes across multiple files.
Multiple agents running in parallel do not automatically sync history; they may each pick conflicting local optima.
Switching to another agent for review is not enough. If the reviewer also lacks the old constraints, it may still approve an architectural regression.
For an agent, the most valuable ADR content is: "Which seemingly reasonable paths have been walked, and why they must not be walked again." It preserves a class of negative knowledge that is hard to reverse-engineer from code.
Practical Advice
AWS and Microsoft ADR guidelines provide a practical set of shared principles:
Record only architecturally significant and hard-to-reverse decisions: system structure, non-functional requirements, dependencies, public interfaces, frameworks, and key processes.
Use a consistent short template; at minimum capture status, context, alternatives, decision, rationale, and consequences.
After Accepted, do not rewrite directly. When a decision changes, create a new ADR and mark the old one Superseded.
Store ADRs centrally, and during code and architecture reviews check whether new changes violate accepted decisions.
A minimal usable template has just five fields: status, context, alternatives, decision, consequences.
In AI programming repositories, I add a reading protocol: before modifying public interfaces, dependencies, security permissions, external side effects, or core structure, the agent must first retrieve relevant Accepted ADRs. Overturning an old decision is allowed, but the agent must first explain why the old approach failed and what conditions have changed. AGENTS.md only needs to note that docs/decisions/ is the accepted ADR directory and which changes require reading them first. Do not copy all ADRs into it. ADR explains the why; types, tests, CI, and runtime validation enforce the boundaries that must not be crossed.
My Practice
In DxC's actual directory, design documents and decision records are separate:
docs/├── README.md├── 02-mvp-technical-design.md├── 03-domain-state-api.md└── decisions/ ├── 0016-cross-platform-onboarding-and-browser-fallback.md ├── 0022-cli-node-22-16-fts5-runtime.md └── 0023-single-forward-workflow-action.mdADR-0023 records a real pitfall. Early DxC exposed multiple advance actions to the host agent, requiring the agent to understand current state and then choose the next command. Actual runs produced wrong action choices, looping calls, and misreporting a single successful response as overall completion.
That ADR finally settled: the public article workflow retains only one advance, with a deterministic kernel deciding what to execute next. It also explicitly rejects extending this interface into a generic action engine.
If you only look at today's code, the agent sees just one advance. Reading the ADR tells it why "adding more flexible actions" might be rebuilding the old problem. In DxC, once an issue enters an Accepted ADR, subsequent agents cannot skip the rationale and re-walk it; when conditions truly change, a new ADR supersedes the old decision.
How to choose: Write an ADR when there are two or more reasonable alternatives, or when a decision affects lots of downstream work and reversal cost is high. Decisions likely to be re-debated in the future are also worth recording. Ordinary implementation details need not be recorded. If AI wants to overturn an old decision, it must first prove conditions have changed.
OpenSpec and Spec Kit: Manage One Change or Manage the Full Spec Chain
Official Function
OpenSpeccenters on a single change, storing proposal (why change), design (how to change), tasks (how to execute), and specs (what must be satisfied when done). After completion it is archived. Suits medium-to-large changes in existing repositories. Spec Kit flows from constitution (project principles), spec, plan, tasks all the way to implement. It fits 0-to-1, multi-role collaboration where spec consistency is the priority.
OpenSpec's official mainline is explore, propose, apply, archive. First explore the problem, then build a proposal and tasks for a single change. After implementation, fold the changes into the current spec. Spec Kit's official core chain is more complete: the project first establishes a constitution, then proceeds through specify → plan → tasks → implement → converge until spec and code are consistent.
Practical Advice
Usually pick only one spec mainline per change to avoid duplicate specs, plans, and tasks. Small, reversible changes doable in one session can skip both. Spec files record goals and state; they cannot replace tests, real-device builds, or human acceptance.
When a team already works around issues, design docs, and existing code, OpenSpec wraps a single change more easily. For a new project that wants the spec to be the primary collaboration artifact and is willing to maintain constitution, spec, plan, and tasks long-term, choose Spec Kit. Do not maintain the same task status simultaneously in OpenSpec, Spec Kit, and an issue system.
DxC and Choral are both existing repositories; they don't need a full spec chain starting from project principles. Spec Kit becomes more suitable for 0-to-1, multi-role projects that continuously maintain specs together.
My OpenSpec Practice
My changes are scoped to one independently verifiable requirement or bug. They may span multiple files but solve only that one problem.
Version splitting happens before the proposal. I first use Superpowers' brainstorming (requirement exploration) or OpenSpec's explore skill to clarify the scope of this round, then split the change. Choral's V1 can be sanitized into a two-level plan:
V1├── Alpha│ ├── foundation│ ├── loop-selection│ └── evaluation-suggestion├── Beta│ ├── loop-strategy-foundation│ ├── measure-gate-loop│ └── practice-mode-guidance└── Release ├── contract-and-local-records ├── history-list-and-replay └── release-hardeningThe upper level manages version scope; each lower item is an independent OpenSpec change. This avoids stuffing all requirements of a version into one proposal, and avoids splitting one cross-file modification into multiple changes that lose business meaning.
Choral is a mixed Flutter, Android, iOS, and C++ project. One real native reverb change has this structure:
openspec/├── config.yaml└── changes/ └── add-native-freeverb-playback-mix/ ├── proposal.md ├── design.md ├── tasks.md └── specs/ ├── native-freeverb-playback-mix/ │ └── spec.md └── cpp-synth-sequencer-runtime/ └── spec.mdI also append three fixed closing tasks at the end of each complete change's tasks.md. Here subagent is a review agent running in an independent clean context:
- [ ] N-2. Implementation report- [ ] N-1. Clean subagent loop review until `VERDICT: PASS`- [ ] N. Human review resultThe implementation report records what was changed, what verification ran, and what was not done. Subagent review loops: if not PASS, the implementation side fixes and re-verifies, then a fresh subagent re-reviews.
Human acceptance depends on functionality. For UI, rendering, animation, interaction, or audio perception, the agent must tell me exactly what to check this round; only explicit human feedback can fill the result. Pure internal changes note "no human experience acceptance needed"; the clean subagent's final PASS becomes the review endpoint.
In the Freeverb change, automated tests and dual-platform compilation passed, but on-device audio, human A/B listening, and upstream dependencies remain incomplete. Machine gate, device gate, and human gate each count separately; none can substitute for the others.
Development Skills: Pick Methods by Failure
Superpowerschains exploration, planning, TDD, implementation, review, and wrap-up into a default flow. Matt Skills can form a complete chain or be taken à la carte for the current task's needs.
Notable Categories in Matt Skills
grill-me/ grill-with-docs: converge requirements through questioning; the latter is repository-aware and incorporates context and ADRs. tdd: first confirm the test boundary (seam — the boundary that can be isolated for testing), then advance vertical slices with failing tests and minimal implementation. implement: execute a confirmed spec or ticket, driving TDD, type checking, and code review. codebase-design: when a module is already chosen, use concepts like module, interface, depth (degree to which a module hides internal complexity), seam to evaluate design. improve-codebase-architecture: when you don't know where to start, scan the repository and produce a candidate report without directly changing code. Ponytail belongs to a complementary category: when agents frequently add abstractions, dependencies, compatibility layers, and future extension points on their own, use YAGNI and minimal implementation to pull the solution back.
Practical Advice
OpenAI's Skills documentation states that a skill's name, description, and path enter the prompt context; the model uses this metadata to decide whether to invoke it. Full skill content also influences planning, tool use, and command execution, so it should be reviewed like high-privilege code and mapped to explicit workflows. OpenAI's model guidance specifically warns: when loading multiple skills and instruction files simultaneously, ambiguous or conflicting rules may cause the model to stop early or deviate from the task. Therefore, actively audit for conflicts.
Activate only the skills necessary for each task. The default execution mainline is singular; each responsibility has one default skill; other capabilities are triggered by specific tasks. When adding or upgrading external skills, pin versions, then check what failures they solve, their trigger conditions, responsibility overlaps, and stop conditions.
My Practice
Choral uses Superpowers, but the root AGENTS.md requires loading only the narrowest skill for the current task:
- Run `openspec list` before any behavior or code work- When Superpowers are needed, read only the `SKILL.md` applicable to the current task- Behavior changes: write failing test first, then implement to pass- After implementation, launch a clean subagent for independent reviewI once triggered grill-me in DxC. It asks one question at a time, first probing what endpoint this development round should reach. I answered a few rounds then actively terminated because the problem wasn't worth a long interview. Ponytail addresses a problem I've hit in both repositories: AI easily proactively adds "might be needed later" abstractions. DxC rejected a generic action engine, complex task orchestration, and backward-compatible old commands. Choral's Freeverb change explicitly does only the minimal C++ implementation inside the project, adding no generic audio processing dependencies, no new routing registry, no new queue, no new clock. Ponytail 's sequence is practical: first ask if the requirement truly exists, then check existing repository capabilities, standard library, platform capabilities, and installed dependencies, and only then write the least new code. It constrains implementation scope; it does not replace safety checks, error handling, or tests.
How to choose: If fixed steps are often missed, use Superpowers. If you already have your own engineering mainline but lack one specific piece — requirement clarification, TDD, implementation driving, or architectural judgment — pick the corresponding Matt Skill. If AI frequently expands solutions on its own, add Ponytail. Do not make all skills default entry points.
Three Project Types, Pick These Three Combos Directly
Personal project, clear boundaries → Minimal combo: Root AGENTS.md + few Skills + ADR + tests / CI. Upgrade when: Changes start crossing sessions or need multi-person handoff.
Complex brownfield system → Minimal combo: AGENTS.md + OpenSpec + one execution method + ADR + multiple acceptance gates. Upgrade when: Spec coordination exceeds a single change.
0-to-1, multi-role collaboration → Minimal combo: AGENTS.md + Spec Kit + deduplicated execution methods + ADR + engineering gates. Upgrade when: Multiple roles continuously fork on the same spec.
Choral falls into the second type; DxC is closer to the first. DxC's confirmation, idempotency (duplicate requests don't produce duplicate results), and external writes are each guarded by programmatic gates. Whether a project needs a heavy workflow depends on handoff cost, cost of missed acceptance, and probability of spec divergence.
If I were reconfiguring DxC today, I would start with a lean AGENTS.md, a few Matt-style skills, ADR, and programmatic gates; only when cross-session change state truly starts getting lost would I add OpenSpec.
A new repository can start with five actions:
Write the root AGENTS.md, containing only scope, truth, boundaries, validation, and routing.
In it, explicitly mark docs/decisions/ as the ADR directory.
Based on the last three real failures, select a few skills.
When cross-session change state genuinely begins to be lost, introduce OpenSpec or Spec Kit.
Put rules that must never be violated into types, tests, CI, permissions, or runtime rejection.
Signed-in readers can open the original source through BestHub's protected redirect.
This article has been distilled and summarized from source material, then republished for learning and reference. If you believe it infringes your rights, please contactand we will review it promptly.
Tech Architecture Stories
Internet tech practitioner sharing insights on business architecture, technology, and a lifelong love of tech.
How this landed with the community
Was this worth your time?
0 Comments
Thoughtful readers leave field notes, pushback, and hard-won operational detail here.
