# agentlint
**ESLint for your AI coding setup.**
Catch broken paths, conflicting instructions, duplicated context, unsafe commands,
leaked secrets, and malformed MCP configuration before your coding agent acts on it.
```text
$ agentlint .
agentlint v0.1.0
AGENTS.md
⚠ AGL302 12:1 Instruction duplicates CLAUDE.md:31.
⚠ AGL601 44:12 Repository uses pnpm, but this instruction requires npm.
.mcp.json
✗ AGL101 8:5 MCP server `filesystem` field `args` must be an array of strings.
✗ AGL401 17:9 Potential secret committed inside agent configuration (`sk-pro...xyz`).
2 files checked · 4 diagnostics · 2 errors · 2 warnings · 0 suggestions
Estimated context: 2137 tokens (94 duplicated)
```
agentlint is local-first. It does not call an AI API, execute commands, start MCP
servers, or send repository data anywhere. It only modifies files when `--fix` is
explicitly supplied.
## Why
Coding-agent configuration quietly becomes production infrastructure. A renamed
script can break every agent. Conflicting package-manager rules create lockfile
churn. A copied instruction burns context in several tools. An MCP token in JSON is
still a committed credential.
agentlint checks these problems deterministically and offline, quickly enough for a
pre-commit hook or every CI run.
## Install
From crates.io after publication:
```sh
cargo install agentlint
```
From a clone:
```sh
git clone https://github.com/zynx-real/agentlint.git
cd agentlint
cargo install --path .
```
### CachyOS and Arch Linux (and other arch based distros)
Rustup is recommended so the project uses a complete, updateable Rust toolchain:
```sh
sudo pacman -S --needed rustup base-devel git
rustup default stable
git clone https://github.com/zynx-real/agentlint.git
cd agentlint
cargo build --release
cargo test
./target/release/agentlint .
```
These commands work from Bash, Fish, and other normal shells. No development script
depends on shell-specific startup files. `yay` is not required for the canonical
Rustup source installation.
## Usage
```sh
agentlint
agentlint .
agentlint path/to/repository
agentlint check
agentlint check path/to/repository
agentlint rules
agentlint explain AGL301
agentlint init
agentlint --format compact
agentlint --format json
agentlint --format github
agentlint --severity warning
agentlint --no-color --quiet
agentlint --fix
```
Exit code `0` means there are no error-severity diagnostics, `1` means lint errors
were found, and `2` means the CLI, configuration, or analyzer failed. JSON mode emits
only its JSON document to stdout; verbose operational messages go to stderr.
`--fix` removes trailing whitespace, formats valid MCP JSON, and corrects
package-manager commands only when the lockfile/package metadata and an existing
package script make the replacement certain. It does not delete instructions or
guess at semantic rewrites.
## Supported configuration
- `AGENTS.md`, `CLAUDE.md`, and `GEMINI.md`
- `.codex/`, `.agent/`, and `.ai/` instruction/configuration files
- `.cursor/*.mdc` and `.cursor/rules/**/*.mdc`
- `.github/copilot-instructions.md` and `.github/instructions/**/*.{md,mdc}`
- `.mcp.json`, `mcp.json`, and JSON/YAML files whose name identifies MCP
- `SKILL.md` at any depth, including `skills/*/SKILL.md`
- JSON, YAML, and TOML configuration under agent directories
Discovery is filename-aware but not filename-bound: classifiers produce typed source
files and independent analysis modules consume those types, so new ecosystems can be
added without restructuring the engine.
## Rules
| AGL001 | error | Malformed JSON, YAML, or TOML |
| AGL002 | error | Malformed or invalid Markdown frontmatter |
| AGL003 | error | Duplicate JSON keys in the same object |
| AGL101 | error | Invalid or incomplete MCP server definitions |
| AGL102 | warning | Obviously unsupported fields |
| AGL103 | error | Malformed or unsupported MCP URLs |
| AGL104 | error | Missing MCP executables |
| AGL105 | warning | Undocumented MCP environment variables |
| AGL201 | error | Invalid instruction globs |
| AGL202 | warning | Missing referenced files/directories |
| AGL203 | error | Missing referenced scripts |
| AGL301 | warning | Instruction files over 6,000 approximate tokens |
| AGL302 | warning | Substantially duplicated cross-file instructions |
| AGL303 | info | Excessively verbose instruction blocks |
| AGL401 | error | High-confidence hardcoded credentials |
| AGL501 | warning | Destructive shell instructions |
| AGL502 | warning | Missing or likely misspelled executables |
| AGL503 | error | Package scripts absent from `package.json` |
| AGL601 | warning | Package-manager conflicts |
| AGL602 | warning | Conservative, pattern-based contradictions |
| AGL603 | warning | Commands inconsistent with project metadata |
Run `agentlint explain AGL302` for the rationale, bad and good examples, default
severity, and disable syntax for any rule. [The complete rule guide](docs/rules.md)
documents behavior and conservative limitations.
Contradiction analysis intentionally handles common imperative forms rather than
claiming general language understanding. Duplicate analysis combines normalized word
sets and edit similarity. Token counts use a local approximate tokenizer and should
be read as context estimates, not provider billing counts.
## Configuration
Run `agentlint init` or create `.agentlint.yaml`, `.agentlint.yml`, or
`.agentlint.json`:
```yaml
rules:
AGL301: warning
AGL401: error
AGL502: off
ignore:
- vendor/**
- examples/**
```
Severities are `off`, `info`, `warning`, and `error`. Pass `--config FILE` to select
a config explicitly and repeat `--ignore GLOB` for invocation-specific exclusions.
agentlint respects `.gitignore` and `.agentlintignore`, plus built-in exclusions for
`.git`, `node_modules`, `vendor`, `dist`, `build`, `target`, `.next`, `.cache`,
`venv`, and `.venv`.
## GitHub Actions
The repository includes its own CI and an integration example at
[`.github/workflows/agentlint.yml`](.github/workflows/agentlint.yml):
```yaml
name: agentlint
on:
pull_request:
push:
jobs:
lint-agent-config:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- uses: dtolnay/rust-toolchain@stable
- run: cargo install agentlint --locked
- run: agentlint --format github
```
## Machine-readable output
`--format json` returns a stable report containing the version, repository root,
file and token counts, diagnostics, optional locations/suggestions/references, and
fixed files. `--format github` emits workflow command annotations. `stylish` is for
people; `compact` is convenient for editor problem matchers.
## Development
```sh
cargo fmt --check
cargo clippy --all-targets --all-features -- -D warnings
cargo test
cargo build --release
./target/release/agentlint .
```
See [CONTRIBUTING.md](CONTRIBUTING.md) for architecture and contribution guidance,
[SECURITY.md](SECURITY.md) for private vulnerability reporting, and
[CODE_OF_CONDUCT.md](CODE_OF_CONDUCT.md) for community expectations.
## License
MIT — see [LICENSE](LICENSE).