Agent harnesses
mdvs ships agent integration in three pieces:
- A skill (the Agent Skills standard) — works in any harness that loads
.mdskills. - A project-rules snippet — works in any harness that reads
AGENTS.md/CLAUDE.md/.cursor/rules. - A PostToolUse hook that calls
mdvs hook handle— only verified end-to-end on Claude Code today.
Per-harness install steps in the left nav.
How violations reach the agent (Claude Code)
When the agent edits a markdown file in your vault:
- The harness’s PostToolUse hook fires the configured
mdvs hook handlecommand. - mdvs reads the tool-call payload, walks up to find
mdvs.toml. If the edit happened outside any vault, the hook stays silent. - mdvs runs
checkon the vault. If the file is clean, the hook stays silent (no noise on the happy path). - If there are violations, mdvs writes a Claude-Code-shaped envelope JSON to stdout. The harness reads it and surfaces the markdown body to the agent through
additionalContextand the pretty render to the user throughsystemMessage. - The agent sees the violation and reacts on its next turn — per the schema-evolution loop: if it’s a mistake, fix the file; if it’s intentional (KB evolving), surface the deviation to the user and propose updating
mdvs.toml.
A separate search-nudge hook fires after every Bash command that runs grep / rg / find / ag / ack / fd / git grep. If the agent’s cwd is inside an mdvs vault, the hook surfaces a one-line tip suggesting mdvs search. Like validate, it’s non-blocking — the agent decides whether to switch tools.
Per-platform support
| Platform | Skill | Snippet | Hooks |
|---|---|---|---|
| Claude Code | ✓ | ✓ | ✓ |
| Codex | ✓ | ✓ | see Codex hooks docs |
| Cursor | ✓ | ✓ | see Cursor hooks docs |
| OpenCode | ✓ | ✓ | see OpenCode docs |
| Antigravity | ✓ | ✓ | see Gemini CLI hooks docs |
Pre-commit hook
A pre-commit hook is a script git runs locally before each git commit — if it exits non-zero, the commit is blocked. The community pre-commit tool manages hooks declaratively per-repo via a YAML config; mdvs plugs into it as a one-line entry.
Running mdvs check as a pre-commit hook catches frontmatter violations before they reach the repo, regardless of how the file was edited — agent, IDE, or by hand. It’s the simplest harness-independent safety net, and the recommended fallback for harnesses where the post-edit hook isn’t wired up.
Install
To install the pre-commit tool on your machine check the docs at this link.
It’s also possible to install pre-commit using uv:
uv tool install pre-commit
Configure
In your mdvs vault, create .pre-commit-config.yaml:
repos:
- repo: local
hooks:
- id: mdvs-check
name: mdvs check
entry: mdvs check --no-update
language: system
pass_filenames: false
Activate the hook in this repo (writes .git/hooks/pre-commit):
pre-commit install
That’s it. The next git commit runs mdvs check; if there are violations the commit aborts and the violation report is printed. To run the check manually without committing:
pre-commit run --all-files
Notes
- Works with any install method.
language: systemjust runs themdvsalready on your PATH — it doesn’t matter whether you installed viacargo install mdvs, the release shell installer, Homebrew, or a manually-placed binary. The only requirement is thatmdvsis invocable from git’s environment. - PATH gotcha for GUI git clients. git pre-commit hooks fire under git’s environment, which isn’t always the same as your interactive shell’s PATH. If
mdvslives in~/.cargo/bin/and you commit from a GUI client that doesn’t inherit your shell PATH, the hook fails withmdvs: command not found. Either commit from the terminal, or use the absolute path inentry:(entry: /Users/you/.cargo/bin/mdvs check --no-update). - Version-pinned alternative. To have
pre-commitfetchmdvsinto its own isolated environment (slower per-repo install, but reproducible across machines and CI), swap tolanguage: rustandadditional_dependencies: ["mdvs"]. --no-updatetellsmdvs checknot to auto-updatemdvs.tomlfrom inferred new fields. The hook validates against the committed schema; schema evolution stays an explicit user action.pass_filenames: falsebecausemdvs checkruns against the whole vault, not file-by-file. The same validation pass covers every staged change in one shot.
For CI-side validation (catches violations even if a contributor skipped the local hook), see the CI recipe.