Are you an LLM? Read llms.txt for a summary of the docs, or llms-full.txt for the full context.
Skip to content

Getting Started

dgov is a local CLI that drives AI coding agents through a deterministic plan/compile/run/review loop. Each task runs in its own git worktree, lands through scoped settlement gates, and leaves an event log you can inspect.

This page walks from a fresh repo to a finished run.

Premise

Most AI coding tooling rests on a hidden assumption: that the model will be careful. dgov rests on the opposite assumption.

A worker is a stranger you let run commands in your repo. It will report tests as passing when no test command ran. It will edit files outside its claimed scope. It will emit done while the working tree is broken. None of that is a bug in the model — it is what a system that samples from text does when the prompt does not constrain it. A better prompt does not fix it. Structure does.

dgov's stance:

  • The orchestrator is a compiler, not an agent. Planning, retries, file claims, and merge decisions are explicit state transitions over an event log. You can read what happened and derive current state from it.
  • Workers are subprocesses, not collaborators. They live in disposable git worktrees, get judged by settlement gates, and merge only after task settlement passes. No shared checkout, no implicit trust.
  • A clean merge is not a clean integration. Shadow integration candidates ask whether the integrated result still works — not just whether git could replay the commit.
  • Plans are contracts. File claims declare legal concurrency; dependencies declare legal order. Compile-time validation rejects conflicting independent claims before any worker runs.
  • Hard gates stop merges. Out-of-scope edits fail review. Configured test failures fail settlement. A missing API key fails before dispatch.

dgov assumes you know what you want to change. It gives you the structure to change it without granting the model unchecked authority over the merge. For workflows that hinge on the model inferring intent from a sentence, a different tool will suit you better.

Requirements

  • Python 3.12+
  • git
  • uv
  • sentrux
  • An OpenAI-compatible API endpoint and key

Install

Install from PyPI:

uv tool install dgov

For a local checkout:

git clone https://github.com/jameshgrn/dgov
cd dgov
uv tool install --from . dgov

The Loop

Plan  →  Compile  →  Run  →  Review

Plans are authored as TOML trees. Compile turns the tree into a normalized DAG. Run dispatches each unit to a worker subprocess in an isolated worktree. Review debriefs the last run, unit by unit. Every step writes to the event log; nothing about lifecycle is implicit.

1. Bootstrap

# Inside a git repo (initialize one if needed)
git rev-parse --is-inside-work-tree >/dev/null || git init
 
dgov init
dgov init --preflight   # optional: print bootstrap and worker-environment checks
dgov agents sync        # optional: refresh local ~/.agents/skills dgov skills
 
# Then edit .dgov/project.toml provider placeholders and export the matching key.
export PROVIDER_API_KEY=your-key-here

dgov init writes three things and detects most of them from the repo:

  • .dgov/project.toml — toolchain commands, LLM providers, tool policy, coverage knobs, scope ignore list.
  • .dgov/governor.md — governor charter: planning rules, retry rules, done criteria.
  • .dgov/sops/*.md — worker SOPs covering architecture, code review, error handling, git commits, large-file handling, Python style, refactoring discipline, return values, state modeling, and testing.

If sentrux is installed and .sentrux/baseline.json does not exist, dgov init offers to create the baseline now. Otherwise run it later:

dgov sentrux gate-save

The baseline is governor-owned state. Worker edits to .sentrux/baseline.json and .sentrux/dgov-baseline.json are rejected during review; a post-run sentrux degradation marks the run degraded and prints a warning. After a clean complete full-plan run, dgov run refreshes the accepted sentrux baseline metadata automatically.

dgov init is idempotent for missing files. Re-running it scaffolds whatever is missing without overwriting existing project config. Pass --force to overwrite. Pass --project-type when auto-detection needs an explicit language hint.

dgov agents sync installs or refreshes shipped dgov machine-agent skills such as dgov-ledger, dgov-plan, and dgov-pane. Their canonical source is agent-guidance/skills/; local ~/.agents/skills/dgov-* copies are derived machine state.

2. Author a plan

Two paths.

Manual. Scaffold an empty plan tree and edit the TOML:

dgov init-plan my-plan --sections tasks

That creates .dgov/plans/my-plan/_root.toml and a tasks/ section directory with a _example.toml you can copy and rename. Underscore-prefixed files are ignored by compile.

A minimal tasks/main.toml:

[tasks.add-feature]
summary = "Add the rate limiter"
prompt = '''
Orient:
Read src/limiter.py before editing. Keep the public API unchanged.
 
Edit:
1. Add token-bucket logic in src/limiter.py.
2. Keep the change scoped to the existing module.
 
Verify:
uv run ruff check src/limiter.py
uv run ty check
'''
commit_message = "feat: token-bucket rate limiter"
files.edit = ["src/limiter.py"]
 
[tasks.add-tests]
summary = "Test the rate limiter"
prompt = '''
Orient:
Read src/limiter.py and the existing test style.
 
Edit:
1. Cover the success path and one over-limit case in tests/test_limiter.py.
 
Verify:
uv run pytest -q tests/test_limiter.py
'''
commit_message = "test: rate limiter coverage"
files.create = ["tests/test_limiter.py"]
files.read = ["src/limiter.py"]
test_cmd = "uv run pytest -q tests/test_limiter.py"
depends_on = ["add-feature"]

See the Plan Reference for the full schema.

Auto. Hand the goal to the planner and it writes the tree for you:

dgov plan create "Add a token-bucket rate limiter to src/limiter.py"

The planner explores the repo, drafts a plan, and writes it to disk. Add --run to compile and execute immediately. Add --auto to skip the planner's clarifying questions.

3. Compile

dgov compile .dgov/plans/my-plan/

Compile walks the tree, merges units, resolves cross-section references, validates the DAG, bundles SOPs, and emits _compiled.toml. SOP bundling calls the LLM unless you pass --dry-run. Pass --graph to print the DAG.

Compile fails closed: malformed SOPs, dangling dependencies, or file-claim conflicts between independent tasks stop the pipeline before any worker runs.

4. Run

dgov run .dgov/plans/my-plan/

dgov run recompiles current source, then dispatches each ready task to a worker subprocess in its own git worktree. Settlement runs after each task: scope review, ruff auto-fix, lint, type-check, targeted tests, sentrux comparison, optional coverage, deterministic Python semantic checks, and integrated-candidate validation. Only candidates that pass settlement merge to the integration branch.

Useful flags:

FlagPurpose
--restartWipe prior run state and start fresh
--continueRetry failed or abandoned tasks from the last run
--only <task>Run a single task and its dependencies
--streamStream worker thoughts and tool calls inline
-v, --verbosePrint per-task duration block at end of run
-y, --yesSkip the bootstrap-commit prompt

If the repo has no commits yet and only .dgov bootstrap files exist, dgov run creates the bootstrap snapshot automatically. If other uncommitted files are present, it asks first.

5. Review

dgov plan review .dgov/plans/my-plan/

Review scopes to the last run via the run-start marker. For each unit it shows: what landed, how many self-corrected tool calls fired before done, the reject reason on failure, and the diff stats. Drill in with --diff <unit> for the full git show and --events <unit> for the worker timeline.

If the plan already auto-archived on success, review resolves to the archive copy and prints a note to stderr.

6. Monitor and recover

dgov status              # one-line summary of the active run
dgov --json status       # same, as JSON
dgov watch               # follow the current live plan
dgov watch --ndjson      # stream app-ready line-delimited JSON
dgov tools audit         # summarize worker tool-call telemetry
dgov clean               # remove stale worktrees and outputs

status, watch, and clean derive state from the event log, not from mutable task snapshots. The event log is the authority.

dgov watch follows the single current live plan by default and switches to a new single live plan when sequential plan runs advance. Use --plan to pin one plan, --all for all-plan history, and --root to watch another checkout/root. Use --ndjson when another process, such as a future desktop app, needs a stable line-delimited stream.

Recovery flows through dgov run:

  • bare dgov run <plan-dir> surfaces abandoned work from a crashed prior run
  • dgov run <plan-dir> --continue retries failed or abandoned tasks
  • dgov run <plan-dir> --restart clears prior run state and starts fresh

7. One-off fixes

For a single-file change you do not need a full plan:

dgov fix "Repair the off-by-one in pagination" -f src/pagination.py
dgov fix "Tighten error messages" -f src/api.py -f src/errors.py

fix scaffolds a transient one-task plan under .dgov/runtime/fix-plans/, compiles it, runs it through the same gates, and archives the plan on success.

Project configuration

.dgov/project.toml carries everything repo-scoped. dgov init detects most of it from the repo. Three blocks worth knowing:

LLM providers — see LLM Providers for full examples:

[project]
provider = "llm"
 
[providers.llm]
default_agent = "provider/model-name"
base_url = "https://provider.example.com/v1"
api_key_env = "PROVIDER_API_KEY"

Tool policy — constrains worker shell-outs:

[tool_policy]
restrict_run_bash = true
deny_shell_commands = ["pip", "python -m pip", "pip3", "python -m venv", "uv venv"]
deny_shell_file_mutations = true
require_wrapped_verify_tools = true
require_uv_run = true

Coverage — optional gate on line-coverage drop. When coverage_cmd is set, run dgov coverage-baseline once. With a baseline and coverage output available, settlement rejects changed files whose coverage drops by more than coverage_threshold percentage points.

coverage_cmd = "uv run pytest --cov=src --cov-report=json:{output} -q"
coverage_threshold = 2.0

Verification recipes — named project-local checks that can be run directly or referenced in task prompts:

[verify.unit]
description = "Run unit tests"
command = "uv run pytest -q -m unit"
dgov verify list
dgov verify run unit

SOP format

.dgov/sops/*.md files follow a fixed shape:

  • front matter: name, title, summary, applies_to, priority
  • sections: When, Do, Do Not, Verify, Escalate

dgov compile validates SOP structure and fails closed on malformed files.

Next steps