Skip to content

release: v0.1.0#18

Merged
brettdavies merged 14 commits intomainfrom
release/v0.1.0
Apr 16, 2026
Merged

release: v0.1.0#18
brettdavies merged 14 commits intomainfrom
release/v0.1.0

Conversation

@brettdavies
Copy link
Copy Markdown
Owner

Summary

Initial release of agentnative (anc) — the agent-native CLI linter. Checks whether CLI tools follow 7
agent-readiness principles across behavioral, source, and project layers.

Cherry-picked all non-docs commits from dev onto origin/main, bumped version, regenerated completions, and generated
CHANGELOG.md per the RELEASES.md runbook.

Changelog

Added

  • Add 30-check agent-readiness scorecard: 8 behavioral, 16 source (Rust + Python), 6 project checks
  • Add --command <name> flag to resolve a binary from PATH and run behavioral checks against it
  • Add default check subcommand — anc ., anc -q ., anc --command rg all work without typing check
  • Add Python source checks: bare-except, sys-exit guard detection, NO_COLOR env handling
  • Add shell completions for bash, zsh, fish, elvish, and powershell

Changed

  • Change --quiet/-q to a global flag for agent discoverability in top-level --help
  • Installed binary is anc (crate name remains agentnative)

Fixed

  • Fix recursive fork bomb when dogfooding anc check . against itself
  • Fix Python sys.exit() false positives in __main__.py and guarded blocks

Documentation

  • Add RELEASES.md documenting the dev/main/release/* workflow and Rust release pipeline
  • Add AGENTS.md with project structure, check inventory, and contribution guide
  • Add complete README.md with 7 principles, install channels, CLI reference, and examples

Type of Change

  • feat: New feature (non-breaking change which adds functionality)

Related Issues/Stories

  • Architecture: docs/plans/2026-04-02-002-feat-release-infrastructure-plan.md (on dev)

Testing

  • Unit tests added/updated
  • Integration tests added/updated
  • Manual testing completed
  • All tests passing

Test Summary:

  • Unit tests: 304 passing (1 ignored: timeout_kills_child)
  • Integration tests: 39 passing

Local verification:

Check Result
cargo fmt --check PASS
cargo clippy -Dwarnings PASS
cargo test PASS (343 tests)
cargo deny check PASS
cargo package PASS
Completions freshness PASS
CHANGELOG versioned section PASS
Guarded paths audit PASS
Provenance guard (all 14 commits) PASS
Windows compat (signal gating) PASS
Dogfood: anc check . PASS (30 checks)
Dogfood: anc --command rg PASS (8 checks)
Shellcheck (all scripts) PASS

Files Modified

89 files changed, 13,789 insertions, 6 deletions (vs origin/main).

Key areas:

  • src/ — full implementation (checks, CLI, runner, project discovery, source analysis)
  • tests/ — integration tests + fixtures (perfect-rust, broken-rust, broken-python, binary-only, source-only)
  • completions/ — shell completions for 5 shells
  • scripts/ — generate-changelog.sh, generate-completions.sh, pre-push hook
  • .github/ — CI workflows, guard workflows, rulesets, PR template
  • CHANGELOG.md, RELEASES.md, README.md, AGENTS.md, CLAUDE.md

Breaking Changes

  • No breaking changes

Deployment Notes

  • No special deployment steps required

Post-merge steps (documented in RELEASES.md):

  1. First-time cargo publish (manual, one-time — Trusted Publishing needs the crate to exist)
  2. Tag push: git tag -a -m "Release v0.1.0" v0.1.0 && git push origin main --tags
  3. release.yml handles: 5-target build, GitHub Release, crates.io publish, Homebrew dispatch

Checklist

  • Code follows project conventions and style guidelines
  • Commit messages follow Conventional Commits
  • Self-review of code completed
  • Tests added/updated and passing
  • No new warnings or errors introduced
  • Changes are backward compatible (or breaking changes documented)

brettdavies and others added 14 commits April 16, 2026 17:25
## Summary

Move `--quiet`/`-q` from the `check` subcommand to the top-level CLI as
a global flag so agents can discover it via `agentnative --help`. Fixes
R8 from the v0.1 plan.

## Changelog

### Changed

- Move `--quiet`/`-q` to global flag visible in top-level `--help` for
agent discoverability

## Type of Change

- [x] `fix`: Bug fix

## Testing

- [x] All 229 unit + 11 integration tests pass
- [x] QuietCheck now passes on self (was Warn)
- [x] Dogfood: 26 pass, 1 warn, 0 fail, 3 skip

## Post-Deploy Monitoring & Validation

No additional operational monitoring required.

---

> **Compound Engineered** with Claude Opus 4.6 (1M context) via ce-work

Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
#7)

## Summary

Bare invocation (`agentnative` with no subcommand) defaulted to `check
.`, causing exponential process growth when
behavioral checks probed the binary. NonInteractiveCheck's bare probe
triggered a full recursive check suite, and
JsonOutputCheck probed subcommands bare (`check --output json`),
compounding the recursion. The tool violated its own P1
(non-interactive) principle.

Two root cause fixes, no depth tracking machinery:
- `arg_required_else_help = true` — bare invocation prints help and
exits instantly (like brew/gh/kubectl)
- Remove bare subcommand probing — always use `--help`/`--version`
suffixes in json_output.rs

## Changelog

### Fixed

- Fix fork bomb when running `agentnative check .` against itself
(dogfooding)
- Fix bare invocation (`agentnative` with no args) to print help instead
of running a full check suite

### Changed

- Change json-output check to WARN (from FAIL) when `--output` flag is
detected but safe probes can't validate JSON
  output (most CLIs ignore `--output` when `--help` is present)

### Documentation

- Add Dogfooding Safety section to CLAUDE.md documenting the two safety
rules for behavioral checks

## Type of Change

- [x] `fix`: Bug fix (non-breaking change which fixes an issue)

## Related Issues/Stories

- Plan: `docs/plans/2026-04-02-001-fix-fork-bomb-dogfood-safety-plan.md`

## Testing

- [x] Unit tests added/updated
- [x] Integration tests added/updated
- [x] Manual testing completed
- [x] All tests passing

**Test Summary:**

- Unit tests: 233 passing
- Integration tests: 12 passing (including dogfood tests completing in
~5s, previously 60s+)
- Manual: verified bare invocation, dogfood check, json output, quiet
mode, principle filter, cross-binary checks,
  bogus subcommands, completions — all instant, zero recursion

## Files Modified

**Modified:**
- `src/cli.rs` — add `arg_required_else_help = true` (1 line, the
primary fix)
- `src/main.rs` — `None` branch → `unreachable!()`, remove unused
`PathBuf` import
- `src/checks/behavioral/json_output.rs` — add subcommand probing,
remove bare `&[]` from safe_suffixes, demote
  unvalidatable probes to WARN
- `src/checks/behavioral/non_interactive.rs` — remove
`is_child`/`AGENTNATIVE_CHECK` branching, always probe bare
- `src/runner.rs` — remove `AGENTNATIVE_CHECK=1` from child process env
- `tests/integration.rs` — add `test_bare_invocation_prints_help`
regression test
- `CLAUDE.md` — add Dogfooding Safety section

## Breaking Changes

- [x] Breaking changes described below:

Bare `agentnative` (no subcommand) now prints help and exits 2 instead
of running `check .`. Users must type
`agentnative check .` explicitly. This matches standard CLI conventions
(brew, gh, kubectl).

## Deployment Notes

- [x] No special deployment steps required

## Checklist

- [x] Code follows project conventions and style guidelines
- [x] Commit messages follow [Conventional
Commits](https://www.conventionalcommits.org/)
- [x] Self-review of code completed
- [x] Tests added/updated and passing
- [x] No new warnings or errors introduced
- [x] Changes are backward compatible (or breaking changes documented)

## Post-Deploy Monitoring & Validation

No additional operational monitoring required — CLI tool with no
runtime/server component.

---------

Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
## Summary

- Add `.github/PULL_REQUEST_TEMPLATE.md` so all PRs follow a consistent
structure with changelog, testing, and checklist sections.

## Type of Change

- [x] `chore`: Maintenance tasks (dependencies, config, etc.)

## Files Modified

**Created:**
- `.github/PULL_REQUEST_TEMPLATE.md`

## Checklist

- [x] Commit messages follow [Conventional
Commits](https://www.conventionalcommits.org/)
- [x] No new warnings or errors introduced
- [x] Changes are backward compatible

🤖 Generated with [Claude Code](https://claude.com/claude-code)

---------

Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
…11)

## Summary

Closes the github-repo-setup and rust-tool-release skill audit findings
that were quick wins, plus resolves todo 003
(single `anc` binary + `agentnative` symlink). Sets up the repo for
v0.1.0 release infrastructure work (Plan 002)
without doing the publish itself.

## Changelog

### Changed

- The installed binary is now `anc`. The crate is still `agentnative`.
Homebrew users will get both `anc` and an
  `agentnative` symlink (formula lands in Plan 002).

### Documentation

- Add `RELEASES.md` documenting the dev/main/release/* workflow and the
Rust release pipeline (crates.io, GitHub
  Releases, Homebrew dispatch).
- README install section now lists all five distribution channels
(Homebrew, cargo install, cargo binstall, GitHub
Releases, from source) and all five shell completions with canonical
auto-loaded paths.

## Type of Change

- [x] `feat`: New feature (single `anc` binary)
- [x] `chore`: Repo setup audit fixes
- [x] `docs`: RELEASES.md, README install section, completions docs

## Related Issues/Stories

- Todo:
`.context/compound-engineering/todos/003-ready-p2-ship-single-anc-binary-with-symlink.md`
(resolved, deleted)
- Skill audits: `github-repo-setup` (6 findings) + `rust-tool-release`
(12 findings) — all quick-win findings
  addressed; remaining work is Plan 002 (release infrastructure)

## Testing

- [x] Unit tests added/updated
- [x] Integration tests added/updated
- [x] Manual testing completed
- [x] All tests passing

**Test Summary:**

- Unit tests: 233 passing (single binary; previously ran twice as 233 ×
2 due to dual `[[bin]]` entries)
- Integration tests: 12 passing, 3 ignored (fixture tests)
- `cargo fmt --check` clean
- `cargo clippy --all-targets -- -D warnings` clean
- `cargo package --list` no longer leaks `.context/`,
`.markdownlint-cli2.yaml`, `scripts/hooks/`
- Pre-push hook (fmt + clippy + test + windows compat) green on every
push

## Files Modified

**Created:**

- `RELEASES.md` — canonical release workflow doc
- `.github/workflows/guard-release-branch.yml` — caller for the reusable
workflow
- `completions/anc.{bash,elvish,fish,powershell,zsh}` — pre-generated
completions
- `scripts/generate-changelog.sh`, `scripts/generate-completions.sh` —
copied from skill templates

**Modified:**

- `Cargo.toml` — single `[[bin]] anc`, removed `default-run`, expanded
`exclude` (added `.context/`,
`.markdownlint-cli2.yaml`, `scripts/`), added Windows binstall override
- `.github/workflows/release.yml` — `bin: anc` (crate stays
`agentnative`)
- `.github/rulesets/protect-main.json` — added `guard-release /
check-release-branch-name` to required status checks
- `src/cli.rs`, `src/main.rs` — `name = "anc"` for clap usage line +
completion generator
- `src/project.rs` — user-facing depth/file-limit warnings reference
`anc check src/`
- `tests/integration.rs` — `Command::cargo_bin("anc")`, version
assertion
- `README.md` — install section, completions section, CLI reference,
contributing
- `AGENTS.md`, `CLAUDE.md` — `anc` for CLI invocations

**Renamed:**

- `.github/PULL_REQUEST_TEMPLATE.md` →
`.github/pull_request_template.md` (lowercase per convention)
- `completions/agentnative.<shell>` → `completions/anc.<shell>` (matches
new binary name)

## Key Features

- **Single `anc` binary** — eliminates the duplicate-build-target
warning and halves test runtime (no more `233 × 2`)
- **All 5 shell completions** generated and committed, named
`anc.<shell>`, README documents canonical auto-loaded
install paths (`~/.local/share/bash-completion/completions/anc`,
`"${fpath[1]}/_anc"`, etc.)
- **Package hygiene** — `cargo package --list` is clean; no dev files
leak into the published crate
- **Release infrastructure docs** — `RELEASES.md` covers the full
dev/main/release/* + tag/publish flow with annotated
  tags (avoids the `tag.gpgsign=true` silent-fail trap)
- **Repo setup parity** — guard-release-branch workflow + ruleset entry
mean release/* is enforced at the workflow
  level, not just by convention

## Benefits

- **Credibility for v0.1.0**: dual licensing, all install channels,
complete completions story, accurate docs
- **Maintainability**: convergence on `RELEASES.md` filename across
brettdavies repos (bird, xurl-rs, agentnative-site
  also updated this session)
- **Agent-readiness for the repo itself**: single binary, no warnings,
package contents auditable

## Breaking Changes

- [x] Breaking changes described below:

The installed executable is now `anc`, not `agentnative`. This only
affects users who installed the crate before today
— and there are none, since v0.1.0 hasn't shipped yet. Homebrew users
will additionally get an `agentnative` symlink
(formula creation is in Plan 002).

Clap's help/version output always shows `Usage: anc` regardless of how
the binary is invoked. Acceptable per the
naming rationale (\`anc\` is the canonical CLI name; `agentnative` is
the project/crate name).

## Deployment Notes

- [x] No special deployment steps required

This PR doesn't trigger a release. v0.1.0 publish happens in Plan 002
via a `release/v0.1.0` branch from main.

## Checklist

- [x] Code follows project conventions and style guidelines
- [x] Commit messages follow Conventional Commits
- [x] Self-review of code completed
- [x] Tests added/updated and passing
- [x] No new warnings or errors introduced
- [x] Changes are backward compatible (or breaking changes documented)

## Additional Context

Three companion repos got related fixes this session (separate
PRs/branches, not in this one):

- `brettdavies/xurl-rs` — fixed bash completion install path bug,
renamed `RELEASING.md` → `RELEASES.md`, all 5 shells
  documented
- `brettdavies/bird` — same `RELEASES.md` rename, 5-shell docs
- `brettdavies/agent-skills` — `rust-tool-release` skill updated to
require canonical completion paths and annotated
  tags

Solutions doc shipped to `brettdavies/solutions-docs`:

`best-practices/shell-completion-install-paths-in-cli-readmes-20260415.md`.

🤖 Generated with [Claude Code](https://claude.com/claude-code)

---------

Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
…-chain pin (#17)

## Summary

Two related hardening efforts bundled:

1. **Convention enforcement** — standardizes all source checks on a
single pattern (`check_x()` returns `CheckStatus`;
`run()` is the sole `CheckResult` constructor, using
`self.id()`/`self.group()`/`self.layer()`). Documents the
convention in CLAUDE.md, refactors all 16 Rust source checks to match,
and adds a Rust-only integration test that
walks the source tree and fails CI if any `check_x()` still returns
`CheckResult`.
2. **Toolchain supply-chain pin** — `rust-toolchain.toml` now pins to a
specific `X.Y.Z` release with a trailing rustc
commit-SHA comment. Rustup verifies component SHA256s from the
distribution manifest, so the pin is effectively a
SHA pin (the manifest is the toolchain's lockfile). Both local and CI
read the same file and install identical
bits. Motivated by a CI-only clippy failure during this PR's own review:
local clippy 1.94 passed a lint that CI
   clippy 1.95 rejected.

Convention enforcement was identified during the [PR #15 code
review](#15)
— the 3 new Python checks were fixed in that PR, but the 16 existing
Rust checks still used the old pattern. The
toolchain pin was added mid-review after the clippy divergence exposed
that floating `channel = "stable"` leaves
local and CI on different rustc versions.

## Changelog

<!-- No user-facing changes — internal refactor + supply-chain
hardening. -->

## Type of Change

- [x] `refactor`: Code refactoring (no functional changes)
- [x] `chore`: Maintenance tasks (supply-chain toolchain pin)
- [x] `docs`: Documentation update (CLAUDE.md conventions + toolchain
policy)
- [x] `test`: Adding or updating tests (convention enforcement test)

## Related Issues/Stories

- Related PRs: #15 (review finding that identified the convention drift)
- Follow-up: `dot-github` todo #4 — determine the automated bump
workflow for `rust-toolchain.toml` across repos
  (central reusable workflow vs. local script vs. hybrid)

## Testing

- [x] Unit tests added/updated
- [x] Integration tests added/updated
- [x] All tests passing

**Test Summary:**

- Unit tests: 304 passing (unchanged count — refactor preserves
behavior)
- Integration tests: 39 passing (+1 new:
`convention_check_x_returns_check_status_not_check_result`)
- Clippy: clean with `-Dwarnings` on rustc 1.94.1 (pinned)

## Files Modified

**Modified:**

- `CLAUDE.md` — added Source Check Convention section (Tier 1) and
Toolchain Pin section documenting the 7-day
  quarantine policy
- `rust-toolchain.toml` — pinned `channel = "1.94.1"` with trailing
comment naming the rustc commit SHA and release
  date; bumped from floating `channel = "stable"`
- `scripts/hooks/pre-push` — removed `rustup update stable` step; pin +
rustup's manifest verification now handle
  toolchain integrity
- 16 files in `src/checks/source/rust/` — `check_x()` returns
`CheckStatus`, `run()` uses `self.id()`/`self.group()`/
  `self.layer()` instead of duplicated string/enum literals
- `src/checks/source/rust/no_pager.rs` — collapsed nested `if` inside a
`match` arm into a match guard (fixes clippy
  `collapsible_match` lint introduced in clippy 1.95)
- `tests/integration.rs` — added
`convention_check_x_returns_check_status_not_check_result` enforcement
test

## Key Details

**Tier 1 (Document):** CLAUDE.md now codifies the source check
structure. Covers the `Check` trait impl shape, the
`check_x() → CheckStatus` separation, and the convention that `run()` is
the sole `CheckResult` constructor. Also adds
a new Toolchain Pin section explaining the supply-chain pin policy.

**Tier 2 (Refactor):** All 16 Rust source checks aligned to the
convention. Net -132 lines by removing duplicated
`CheckResult` construction (previously the `id` / `label` / `group` /
`layer` fields were hardcoded in both `run()`
and every `check_x()` helper).

**Tier 3 (Enforce):** Integration test walks `src/checks/source/` with
`std::fs` (no shell dependencies), finds every
`fn check_` signature (any visibility, single-line or multi-line), and
fails if any return `CheckResult` instead of
`CheckStatus`. Uses `CARGO_MANIFEST_DIR` for a stable absolute path.

**Toolchain pin format:** `channel = "1.94.1" # rustc
e408947bfd200af42db322daf0fadfe7e26d3bd1, released 2026-03-25`.
Comment mirrors the GitHub Actions SHA-pin pattern (`action@<sha> #
vN.N.N`). Policy: bump only via reviewed PR after
the new stable has aged ≥7 days (supply-chain quarantine consistent with
`UV_EXCLUDE_NEWER` / bun
`minimumReleaseAge` / `npm_config_min_release_age` in dotfiles).

## Benefits

- Eliminates ID string literal triplication (3 copies per check → 1
authoritative source in `fn id()`)
- New checks can't drift — the convention is documented AND enforced by
CI
- -132 lines of boilerplate removed
- Local and CI toolchains are guaranteed identical — no more "local
clippy older than CI clippy" false greens
- Toolchain updates route through reviewed PRs with a 7-day quarantine,
matching the broader brettdavies supply-chain
  posture

## Breaking Changes

- [x] No breaking changes

## Deployment Notes

- [x] No special deployment steps required

## Checklist

- [x] Code follows project conventions and style guidelines
- [x] Commit messages follow Conventional Commits
- [x] Self-review of code completed
- [x] Tests added/updated and passing
- [x] No new warnings or errors introduced
- [x] Changes are backward compatible
Reflects the single-[[bin]] crate: agentnative ships anc, not anc plus
an agentnative symlink. Updates README install example and RELEASES.md
homebrew-dispatch row to match.
RELEASES.md: "draft GitHub Release" → "non-draft with make_latest: false"
to match the actual release.yml pipeline behavior.

rust-toolchain.toml: release date comment 2026-03-25 → 2026-03-26.
@brettdavies brettdavies merged commit 93a0b36 into main Apr 16, 2026
9 checks passed
@brettdavies brettdavies deleted the release/v0.1.0 branch April 16, 2026 23:06
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.

1 participant