|
| 1 | +# AGENTS.md — xtask-watch |
| 2 | + |
| 3 | +Guidelines for agentic coding tools working in this repository. |
| 4 | + |
| 5 | +--- |
| 6 | + |
| 7 | +## Repository Overview |
| 8 | + |
| 9 | +`xtask-watch` is a Rust library crate providing a `Watch` helper that relaunches a |
| 10 | +command when source files change. It also exposes a `WatchLock` / `WatchLockGuard` pair |
| 11 | +so external readers (e.g. an HTTP dev-server) can coordinate with ongoing rebuilds. |
| 12 | + |
| 13 | +``` |
| 14 | +xtask-watch/ |
| 15 | +├── src/ |
| 16 | +│ └── lib.rs # Entire library (single-file crate) |
| 17 | +├── examples/ # Usage examples |
| 18 | +└── .github/workflows/ # CI definitions |
| 19 | +``` |
| 20 | + |
| 21 | +--- |
| 22 | + |
| 23 | +## Build, Lint, and Test Commands |
| 24 | + |
| 25 | +All commands are run from the repository root unless noted otherwise. |
| 26 | + |
| 27 | +### Standard check/build |
| 28 | +```bash |
| 29 | +cargo check --workspace --all-features |
| 30 | +cargo build --workspace --all-features |
| 31 | +``` |
| 32 | + |
| 33 | +### Run all tests |
| 34 | +```bash |
| 35 | +cargo test --workspace |
| 36 | +``` |
| 37 | + |
| 38 | +### Run a single test |
| 39 | +```bash |
| 40 | +# By test name (substring match) |
| 41 | +cargo test <test_name> |
| 42 | +``` |
| 43 | + |
| 44 | +### Formatting |
| 45 | +```bash |
| 46 | +# Check (CI uses this) |
| 47 | +cargo fmt --all -- --check |
| 48 | + |
| 49 | +# Apply |
| 50 | +cargo fmt --all |
| 51 | +``` |
| 52 | + |
| 53 | +### Linting (clippy) |
| 54 | +```bash |
| 55 | +# CI command — all warnings are errors |
| 56 | +cargo clippy --all --tests --all-features -- -D warnings |
| 57 | + |
| 58 | +# Local (softer, same flags) |
| 59 | +cargo clippy --all --tests --all-features |
| 60 | +``` |
| 61 | + |
| 62 | +### CI matrix |
| 63 | +CI runs on stable Rust and the MSRV declared in `Cargo.toml` (`rust-version`). Always |
| 64 | +verify `cargo fmt` and `cargo clippy` pass before committing. |
| 65 | + |
| 66 | +Current MSRV: **1.85.1** (Rust edition 2024). Do not use features introduced after this |
| 67 | +version without updating `rust-version` in `Cargo.toml`. |
| 68 | + |
| 69 | +--- |
| 70 | + |
| 71 | +## Changelog — MANDATORY |
| 72 | + |
| 73 | +**Every pull request or commit that contains a user-visible change MUST add an entry to |
| 74 | +`CHANGELOG.md` under the `## [Unreleased]` section.** This is not optional. |
| 75 | + |
| 76 | +### What counts as user-visible |
| 77 | + |
| 78 | +- New public types, functions, methods, or trait impls |
| 79 | +- Changed behaviour of existing public API |
| 80 | +- Bug fixes observable by users |
| 81 | +- Dependency version bumps that affect the public API or MSRV |
| 82 | +- Removed or renamed public items |
| 83 | + |
| 84 | +### What does NOT need a changelog entry |
| 85 | + |
| 86 | +- Internal refactors with no observable behaviour change |
| 87 | +- CI / tooling changes |
| 88 | +- Documentation-only changes (though you may add a `### Documentation` entry if useful) |
| 89 | + |
| 90 | +### Format |
| 91 | + |
| 92 | +Follow the [Keep a Changelog](https://keepachangelog.com/en/1.0.0/) format already |
| 93 | +in use. Add a subsection under `## [Unreleased]` using one of: |
| 94 | + |
| 95 | +```markdown |
| 96 | +## [Unreleased] |
| 97 | + |
| 98 | +### Added |
| 99 | +- Short description of the new thing (#PR). |
| 100 | + |
| 101 | +### Changed |
| 102 | +- Short description of what changed and why (#PR). |
| 103 | + |
| 104 | +### Fixed |
| 105 | +- Short description of the bug that was fixed (#PR). |
| 106 | + |
| 107 | +### Removed |
| 108 | +- Short description of what was removed (#PR). |
| 109 | +``` |
| 110 | + |
| 111 | +Use the imperative mood ("Add …", "Fix …", "Remove …"). Reference the PR or issue |
| 112 | +number in parentheses when one exists. |
| 113 | + |
| 114 | +### When to write the entry |
| 115 | + |
| 116 | +Write the changelog entry **in the same commit as the code change**, not afterward. |
| 117 | +If you forget, the release will go out with an empty `[Unreleased]` section and the |
| 118 | +change will be invisible to users of the crate. |
| 119 | + |
| 120 | +--- |
| 121 | + |
| 122 | +## Code Style Guidelines |
| 123 | + |
| 124 | +### Formatting |
| 125 | + |
| 126 | +- Use `cargo fmt` (default `rustfmt` settings — no `rustfmt.toml` in this repo). |
| 127 | +- 4-space indentation; no tabs. |
| 128 | +- Trailing commas in multi-line struct literals and function call arguments. |
| 129 | + |
| 130 | +### Imports |
| 131 | + |
| 132 | +- Group imports using nested paths where possible: |
| 133 | + ```rust |
| 134 | + use std::{path::PathBuf, process::Command, sync::Arc}; |
| 135 | + ``` |
| 136 | +- Standard library imports first, then external crates, then `crate::` / `super::`. |
| 137 | + |
| 138 | +### Naming Conventions |
| 139 | + |
| 140 | +| Item | Convention | Example | |
| 141 | +|------|-----------|---------| |
| 142 | +| Types / traits | `PascalCase` | `Watch`, `WatchLock` | |
| 143 | +| Functions / methods | `snake_case` | `run_command`, `handle_event` | |
| 144 | +| Fields / variables | `snake_case` | `watch_paths`, `debounce` | |
| 145 | +| Constants / statics | `SCREAMING_SNAKE_CASE` | `METADATA` | |
| 146 | +| Modules | `snake_case`, match filename | `lib` | |
| 147 | + |
| 148 | +### Error Handling |
| 149 | + |
| 150 | +- All fallible functions return `anyhow::Result<T>`. |
| 151 | +- Prefer `.context("…")` / `.with_context(|| …)` to annotate errors. |
| 152 | +- `unwrap()` is acceptable only when the invariant is guaranteed by surrounding logic. |
| 153 | +- `expect("message")` is acceptable where a panic would indicate a programmer bug. |
| 154 | +- Do **not** introduce custom error types — stay with `anyhow` throughout. |
| 155 | + |
| 156 | +### Types and Traits |
| 157 | + |
| 158 | +- Public API structs are marked `#[non_exhaustive]` to preserve semver compatibility. |
| 159 | +- Public API structs that are CLI entry points derive `clap::Parser`. |
| 160 | +- Builder pattern: methods take `mut self` and return `Self` for chaining. |
| 161 | + |
| 162 | +### Documentation |
| 163 | + |
| 164 | +- `#![deny(missing_docs)]` is active in `lib.rs` — **every public item must have a doc |
| 165 | + comment**. |
| 166 | +- Use `///` for item-level docs; `//!` for module/crate-level docs. |
| 167 | +- Include `# Examples` sections (with ` ```rust,no_run ``` `) for significant public API. |
| 168 | + |
| 169 | +### Logging |
| 170 | + |
| 171 | +- Use the `log` crate macros: `log::trace!`, `log::debug!`, `log::info!`, `log::warn!`, |
| 172 | + `log::error!`. |
| 173 | +- Do not use `println!` / `eprintln!` for diagnostic output. |
| 174 | + |
| 175 | +--- |
| 176 | + |
| 177 | +## Dependency Philosophy |
| 178 | + |
| 179 | +- Keep dependencies minimal. |
| 180 | +- `anyhow`, `clap`, `cargo_metadata`, and `camino` are re-exported for downstream crates |
| 181 | + (e.g. `xtask-wasm`) — preserve these re-exports. |
| 182 | +- `glob` and `lazy_static` are internal implementation details; do not re-export them. |
| 183 | +- `libc` is a Unix-only dependency (`[target.'cfg(unix)'.dependencies]`); guard any |
| 184 | + libc usage with `#[cfg(unix)]`. |
| 185 | + |
| 186 | +--- |
| 187 | + |
| 188 | +## Platform-Specific Code |
| 189 | + |
| 190 | +- Unix-only code (e.g. `SIGTERM` signalling) must be wrapped in `#[cfg(unix)]` blocks. |
| 191 | +- Windows must still compile and behave correctly — fall back gracefully where POSIX |
| 192 | + primitives are unavailable. |
| 193 | + |
| 194 | +--- |
| 195 | + |
| 196 | +## MSRV Policy |
| 197 | + |
| 198 | +The minimum supported Rust version is declared in `Cargo.toml` under `rust-version`. CI |
| 199 | +verifies both stable and MSRV. Do not use language or library features introduced after |
| 200 | +that version without updating `rust-version` **and** adding a `### Changed` entry to the |
| 201 | +changelog. |
0 commit comments