Back to Discover

disciplined-agentic-engineering

skill

swingerman

Acceptance Test Driven Development for Claude Code — inspired by Uncle Bob's approach from empire-2025

View on GitHub
129 starsMITSynced Aug 2, 2026

Install to Claude Code

/plugin marketplace add swingerman/disciplined-agentic-engineering

README

Disciplined Agentic Engineering (DAE)

A methodology kit for engineering-led AI development — spec-driven, test-driven, charter-bound. ATDD + mutation testing + deterministic guardrails.

License: MIT Reference host: Claude Code

AI agents do the typing. Engineers stay in charge of architecture, behavior contracts, and verification. DAE puts the discipline in deterministic tools the agent has to satisfy — not in prompt rules that erode over long runs.

The methodology is host-independent. It ships today as three plugins for Claude Code, the reference host — see Host independence.

ℹ️ Repo renamed from swingerman/atdd. Old URLs still redirect; update remotes only if you want to: git remote set-url origin https://github.com/swingerman/disciplined-agentic-engineering.git


Contents

Quick start · Install · Your first featureGet running
How it works · The pipeline · Guardrails · AutonomyThe methodology
The three plugins · engineer · atdd · crap-analyzerWhat's in the box
Host independencePorting to another runtime
Why not vibe coding · Who it's for · BackgroundThe argument
Repo layout · ContributingReference

Quick start

Install

On Claude Code:

/plugin marketplace add swingerman/disciplined-agentic-engineering

/plugin install engineer@disciplined-agentic-engineering      # the DAE methodology kit
/plugin install atdd@disciplined-agentic-engineering          # ATDD + differential mutation testing
/plugin install crap-analyzer@disciplined-agentic-engineering # change-risk analysis

Or run from a clone:

git clone https://github.com/swingerman/disciplined-agentic-engineering.git
claude --plugin-dir ./disciplined-agentic-engineering

Your first feature

/engineer.onboard        # once per project — charter, manifest, tracker
/engineer.next           # every session — "what should I pick up?"
/engineer.discuss        # an idea → drop, park, or promote to a feature

From there the pipeline tells you the next command at every step. Each checkpoint ends with a handoff naming what comes next, and /engineer.next reconstructs that at any time.


How it works

DAE operates on features — numbered folders that accumulate a stack of progressively-sharper specs, Speckit-style:

feature.md  →  acs.md   →  spec.md   →  plan.md
intent         behavior     Gherkin      architecture
               (domain      (executable)
                language)

Each layer is reviewed and approved before the next is written, and constrains the ones below it. The folder also holds handoffs/ (the audit trail) and .build/ (generated IR and pipelines).

The pipeline

Eight checkpoints, each gated on the previous one's handoff:

0 Onboard → 1.5 Ready → 2 ACs → 3 Spec → 4 Plan → 5 Implement → 6 Refine → 7 Verify → 8 Harden
#StageCommandWhat happens
0Onboard/engineer.onboardOnce per project. Human signs off the charter (architecture, conventions, quality + autonomy stance); manifest and features/ layout produced.
1.5Ready/engineer.feature-initfeature.md records outcome, scope, owner, autonomy level, branch. The contract for what we're building.
2ACs/engineer.discover-acsFour-pass interview — happy path, edges, errors & security, cross-cutting. Output acs.md in domain language. Reviewed by an adviser + devil's-advocate panel.
3Spec/engineer.atddatdd:atddACs become standard Gherkin in spec.md; a project-specific test pipeline is generated. Leakage caught by spec-guardian.
4Plan/engineer.planArchitecture plan + structured Charter Check. Human confirms the architecture before the rest drafts. Panel-reviewed.
5Implement/atdd:atdd-teamFresh-per-phase agent team implements against the specs. Two test streams (acceptance + unit) must go green together.
6Refine/engineer.refineParallel review across Reuse / Quality / Efficiency, fed deterministic duplicate findings, filtered through the charter.
7Verify/engineer.arch-check + crap-analyzerArchitecture fitness (layering, cycles, forbidden patterns, naming, size) + change-risk on the diff. A different agent than the implementer.
8Harden (optional)/atdd:atdd-mutateDifferential mutation testing proves the unit tests actually catch bugs.

Cross-cutting, any time: clarify · consistency-check · feature-edit · progress-log · reorient · session-summary · next.

The guardrails

Every checkpoint is gated by tools, not by prompt rules. An agent can talk itself out of an instruction; it cannot talk itself out of a non-zero exit code. At each checkpoint's Step 0:

GateScriptEnforces
Entrydae_handoff.pyThe prior checkpoint's handoff exists, status: complete, every exit criterion met
Branchdae_branch.pyYou're on the feature's branch (git.manual: true opts out)
Ontologydae_ontology.pyArtifact-graph constraints — enumerations, AC↔scenario coverage, verifier ≠ implementer
Breadcrumbdae_progress.pyPassive "you are here" across the pipeline + roadmap

All 21 scripts are stdlib-only Python 3, each with a test_*.py sibling — 483 tests. No dependencies is a deliberate portability constraint, not an aesthetic one.

The full guardrail set (21 scripts)
ScriptPurpose
dae_resolve.pyMethodology-root + manifest resolver; central schema validation
dae_handoff.pyHandoff-as-gate; project-wide status survey
dae_branch.pyBranch hygiene at every checkpoint entry
dae_progress.pyPipeline breadcrumb + roadmap position
dae_ontology.pyArtifact-graph constraint checks (see references/ontology.md)
dae_arch.pyArchitecture fitness — layering, cycles (Tarjan's SCC), naming, file size
dae_impact.pyTest Impact Analysis — run only the scenarios a change affects
dae_mutmap.pyDifferential mutation — re-mutate only what changed
dae_dup.pyDuplicate-code detection (jscpd by default, configurable), fed into Refine's Reuse lens
dae_gherkin.pyPortable Gherkin → IR parser (+ _convert, _mutate siblings)
dae_reconcile.pyReconciles feature state against git/PR reality
dae_release.pyVersion bump + cache sync for the plugins themselves
dae_commit.pyCommit with bounded retry and safe stale-lock removal
dae_roadmap.py · dae_tracker_local.pyRoadmap + tracker drivers
dae_delegable.pyCloud-vs-local dispatch routing
dae_infra.pyDeclared infrastructure probe / start / teardown
dae_introvert.pyFlags tests that pass without asserting on output
dae_fix.pyBug-fix lifecycle + gap analysis

Handoffs

Every agentic task ends with a structured handoff — frontmatter plus body — carrying its checkpoint, artifacts, exit-criteria assertions, panel findings, and recommended_next. Two jobs:

  • You know when to re-engage after walking away.
  • The next checkpoint's entry gate uses it to decide whether it may proceed.

A checkpoint is not done until its handoff says so and the tools agree.

Tunable autonomy

Every feature carries an explicit autonomy level — how much the agent decides alone versus asking for sign-off. Set at feature-init, recorded in feature.md, constrained project-wide by .engineer/manifest.yml's autonomy.allowed_levels, tightened for sensitive paths (security, billing) via path overrides.

LevelBehavior
lowConfirm before dispatching the next checkpoint. Review-everything mode.
mediumAuto-dispatch, announced in one line.
highAuto-dispatch silently; report outcomes. "Agent, go cook."

Some gates ignore the dial: plan always asks the human to confirm the architecture, and outward-facing writes (pushing to main, opening or merging PRs, self-modifying agent config, writing to live systems) always require explicit authorization — even at high.

Worked example — feature 015, idea to merge
# Session 1 — idea to spec
$ /engineer.discuss
  [brainstorm: "add image upload to user profile"] → promote (autonomy: medium)
  Created features/015-image-upload/{feature.md, handoffs/, .build/} + branch

$ /engineer.discover-acs
  [four-pass interview] → acs.md, 8 ACs in domain language
  [adviser + advocate panel] → 2 findings, 1 accepted
  Handoff → human review

$ /engineer.atdd
  → spec.md (4 scenarios, standard Gherkin) + .build/spec.json + test pipeline

# Session 2 — plan and build
$ /engineer.plan
  [agent proposes architecture; human confirms; rest drafts]
  → plan.md (Charter Check: 0 deviations)

$ /atdd:atdd-team
  [fresh agent per phase] → both test streams green
  [refine → arch-check → crap-analyzer → differential mutation]

# Session 3 — wrap
$ /engineer.session-summary
  → session-log.md, next-tasks: open the PR

At every step the entry gate verifies the prior handoff, the branch check verifies you're on image-upload, and the breadcrumb shows where you are in the pipeline and on the roadmap.


The three plugins

PluginPurposeVersion
engineerThe DAE methodology kit — 18 skills, 21 guardrail scripts, the checkpoint pipeline0.21.0
atddATDD workflow, team orchestration, differential mutation testing, portable Gherkin pipeline0.8.2
crap-analyzerChange Risk Anti-Pattern analysis on changed code0.1.1

engineer — the methodology kit

All 18 skills
SkillRole
onboardProject bootstrap — charter, manifest, tracker (CP0)
discussUpstream funnel — brainstorm; drop / park / promote
feature-initProduces feature.md, folder, branch, tracker entry (CP1.5)
prime-contextOrient on a Ready feature before AC discovery
discover-acsAC discovery interview → acs.md (CP2)
atddCP3 entry point — bridges into atdd:atdd
planArchitecture plan + Charter Check → plan.md (CP4)
refineParallel reuse / quality / efficiency review (CP6)
arch-checkArchitecture fitness — layering, cycles, naming, size (CP7)
fixBug lifecycle, with a "why didn't we catch it?" gap analysis
reorientMid-task re-anchoring after compaction or a long run
clarifySingle-artifact ambiguity resolution
consistency-checkCross-artifact validation, read-only
feature-editIntent-driven edits with downstream cascade
progress-logHandoffs → progress.md + tracker sync
session-summaryPer-session session-log.md entry
post-mergeBranch cleanup + state reconcile after a merge
nextSession-start survey — what to pick up now

Deeper detail lives in the repo, not here: engineer/skills/*/SKILL.md for each skill's workflow and exit contract, and engineer/references/ for the shared contracts — handoff schema, progress indicators, review panel, model classes, host capabilities, ontology, parallelism, and more.

atdd — Acceptance Test Driven Development

"Specs will be co-authored by the humans and the AI, but with final approval, ferociously defended, by the humans." — Robert C. Martin

Packages Robert C. Martin's approach to applying ATDD against agentic AI coding, as developed in empire-2025.

Two problems it solves. Without acceptance tests anchoring behavior, an agent "willy-nilly plops code around" and writes unit tests that pass without verifying anything worthwhile. And left alone, agents fill Given/When/Then with class names, endpoints, and table names instead of domain language.

/atdd:atdd Add user authentication with email and password
/atdd:spec-check     # audit specs for implementation leakage
/atdd:mutate         # verify the tests actually catch bugs
/atdd:kill-mutants   # write tests targeting survivors

The Golden Rule: specs describe what the system does, never how.

❌ Implementation leakage✅ Domain language
Given the UserService has an empty userRepositoryGiven there are no registered users
When a POST is sent to /api/users with JSON bodyWhen a user registers with email "bob@example.com"
Then the database contains 1 row in usersThen there is 1 registered user
The loop, and what a spec looks like
1. Write Given/When/Then specs — natural language, domain only
2. Generate the test pipeline (parser → IR → test generator),
   which has deep knowledge of your codebase internals
3. Run acceptance tests → they FAIL (red)
4. Implement with TDD until BOTH streams pass
5. Review specs for implementation leakage
6. Mutation testing → verify the tests actually catch bugs
7. Next feature, back to 1

Specs are standard Gherkin in spec.md:

Feature: User registration

Scenario: User can register with email and password
  Given no registered users
  When a user registers with email "bob@example.com" and password "secret123"
  Then there is 1 registered user
  And the user "bob@example.com" can log in

Migrating from the legacy ;=== .txt format? Run dae_gherkin_convert.py specs/feature.txt features/NNN-slug/spec.md from the engineer plugin's scripts/. The .txt format is deprecated.

Three validation layers, each answering a different question:

LayerAsks
Acceptance testsWHAT — does the external behavior match the contract?
Unit testsHOW — is the internal structure right?
Mutation testingREAL? — do those tests actually catch bugs?

Differential mutation testing keeps layer 3 affordable: dae_mutmap.py maintains a committed manifest keyed by function, and re-mutates one only when its code, its covering tests, or the operator set changed. The hash triple makes the cache safe to share across CI, fresh clones, and every developer.

atdd plugin components
ComponentNamePurpose
Skillatdd7-step workflow: specs → pipeline → red/green → iterate
Skillatdd-teamFresh-per-phase agent team across six phases
Skillatdd-mutateMutation testing with differential re-runs
Agentspec-guardianCatches implementation leakage in Given/When/Then
Agentpipeline-builderGenerates a bespoke parser → IR → test generator
HookPreToolUseWarns when writing code without acceptance specs
HookStopReminds you to verify both test streams

The generated pipeline is not Cucumber — "a strange hybrid of Cucumber and the test fixtures" (Uncle Bob). The parser/generator has deep knowledge of your system's internals and emits complete, runnable tests. No manual fixture code.

crap-analyzer — change risk

Change Risk Anti-Pattern analysis over changed code: complexity × lack of coverage, scoped to a diff. Multi-language. Part of Checkpoint 7 alongside arch-check.


Host independence

DAE is a methodology, not a set of host features wearing a methodology's name. The pipeline, the checkpoint contract, the artifact schemas, and the dae_*.py guardrails are host-independent by construction — stdlib-only Python 3 with no dependencies, precisely so that stays true.

What is host-specific is the mechanism each capability is reached through. The skills name Claude Code's mechanisms directly ("dispatch via the Agent tool") because that's the host they run on today — but those names are bindings, not the contract. engineer/references/host-capabilities.md holds the seam:

Capabilities
Requireddispatch a fresh agent · filesystem · script execution
Optionalprogress surface · structured ask · orchestration · isolation · remote execution · peer messaging · tool channels · rendered views

Every optional capability has a specified degradation, so a host that lacks one loses a convenience, never the methodology. Porting is editing that table's binding column, plus the plugin-root path prefix and the host hook examples.

The same discipline applies to models: engineer/references/model-classes.md names capability classeseconomy / inherit / frontier — rather than product names, which get deprecated, and resolves them against the host's live model list at dispatch time.

Optional capabilities are used when present and never depended on. A rendered board is a better answer to "where are we" than four lines of breadcrumb, so DAE offers one where the host can publish views — and always emits the terminal text regardless.


Why not vibe coding

Vibe coding is prompting loosely — "build me a thing that does X" — accepting what comes back, running it, patching when something feels off. No charter, no behavior contract, no verification gates. Fast at first, brittle over time: the codebase drifts, tests pass without proving anything, regressions surface when users find them.

Vibe codingDAE
Architectureemerges from promptsengineered upfront; CHARTER.md enforced by arch-check
Behavior contract"whatever the agent built"ACs + Gherkin, human-approved, leakage-checked
Verificationrun it and seetwo test streams + change-risk + mutation testing
Gatesnonehandoff-as-gate, branch hygiene, ontology, exit criteria
Refactoring safetytests may not catch regressionsmutation-tested suite = semantic firewall
Autonomyimplicit, driftsexplicit per feature, manifest-constrained
Discipline lives ina prompt (and erodes)tools the agent can't argue with
Pacefast initiallysteady, sustainable

Shipping something quick and disposable? Vibe coding is fine. Building something you intend to maintain — with agents helping without eroding what they touch? That's what this is for.

The headline outcome is semantic stability. ATDD plus mutation testing form a semantic firewall: code can be refactored, extended, or rewritten by agents without the system's intended behavior drifting.

Who it's for

Software engineers. DAE assumes you can read a plan.md and judge whether the architecture is sound; read a Gherkin spec and tell whether it captures intent; know when a charter rule should be enforced versus amended.

Not for non-programmers. "Build an app without code" tools target a different audience and a different problem. The decisions DAE puts in front of you — architecture, behavior contracts, charter rules, verification thresholds, autonomy levels — are engineering decisions that need engineering judgment.

Background & influences

Programming has always climbed the abstraction ladder: front-panel switches → punch cards → assembly → high-level languages → managed runtimes → and now, with capable LLMs, specification and behavior description as the next rung. At every step the rung below fades from daily concern. Nobody hand-writes opcodes; nobody audits the assembly a compiler emits.

What never shifts is engineering discipline. Compiler output earned trust because the compiler was rigorous and the inputs were checked. AI-generated code earns it the same way: rigorous input artifacts (charter, ACs, specs, plans) and checked output (two test streams, mutation testing, architecture fitness, change risk, duplicate and cycle detection). Change the artifact you author but stop checking the output, and you don't get speed — you get a faster path to a brittle system.

DAE synthesizes four sources:

SourceWhat DAE takes from it
ATDD (XP / FIT / Fitnesse lineage — Kent Beck, Ward Cunningham, others)Acceptance tests as a behavior contract. Uncle Bob's empire-2025 showed its particular power as a constraint on agentic development — two test streams the agent can't talk past, plus mutation testing as the test-quality firewall.
SpeckitSpecification is iterative and layered, not a one-shot document. Each feature evolves through progressively-sharper specs, each approved before the next.
Acceptance Pipeline Specification (Uncle Bob, 2026)Portable pipeline: Gherkin → JSON IR → generated tests → runner, with mutation as an IR-level sidecar.
The host's stock /simplifyThe three-lens parallel review pattern (Reuse / Quality / Efficiency). DAE's refine adds charter validation of every proposal and graceful breaking-change classification.

Two further debts to Uncle Bob's public writing on ATDD, SDD, and AI-assisted development: the swarm-failure observations that drove DAE's deterministic-guardrail philosophy, and the differential-mutation post that shaped dae_mutmap.py.

DAE's own additions: the Ready contract, autonomy levels, verification independence, the handoff / exit-criteria contract, the artifact ontology, the review panel, and the deterministic dae_*.py guardrails.

This marketplace contains no code from empire-2025 or other upstream projects — it adapts the methodology.


Repo layout

.
├── .claude-plugin/          # marketplace + atdd plugin manifests
├── agents/ commands/        # atdd plugin agents and commands
├── hooks/ references/       # atdd plugin hooks and references
├── skills/                  # atdd plugin skills (atdd, atdd-team, atdd-mutate)
│
├── engineer/                # the DAE methodology kit
│   ├── references/          # shared contracts — handoff, ontology, panel,
│   │                        #   model classes, host capabilities, parallelism
│   ├── scripts/             # dae_*.py guardrails + their unit tests
│   ├── skills/              # the 18 engineer skills
│   └── examples/            # optional host hook configs
│
└── crap-analyzer/           # change-risk analysis plugin

Contributing

Issues and PRs welcome on GitHub.

License

MIT

Rendered live from swingerman/disciplined-agentic-engineering's GitHub README — not stored, always reflects the source repo.

3 Plugins

NameDescriptionCategorySource
atddAcceptance Test Driven Development for Claude Code. Enforces the ATDD methodology: write Given/When/Then specs first, generate a project-specific test pipeline, maintain two test streams (acceptance + unit). Inspired by Robert C. Martin's acceptance test approach from empire-2025.development-workflows./
engineerDisciplined Agentic Engineering (DAE) — methodology kit for Claude Code. Skills that implement the DAE pipeline: feature intake, AC discovery, spec writing, planning, implementation, verification, hardening.development-workflows./engineer
crap-analyzerAnalyze recently-changed code for Change Risk Anti-Patterns. Multi-language (TS/JS, Python, Java, Kotlin, Go, Ruby, C#, Rust, PHP) with auto-discovered coverage toolchain. Part of DAE's Light Verify tier (Checkpoint 7).code-quality./crap-analyzer

0 Comments

Login required
Log in to post a comment or update on this repo.

No comments yet — be the first to share an update.