You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
@@ -27,16 +27,19 @@ Your source code never leaves your environment. Works offline. Ships as a **sing
27
27
28
28
## Features
29
29
30
+
-**Deterministic pre-filter** — lockfiles, generated files, minified bundles, assets and formatting-only hunks are dropped before the model sees them, and the run tells you exactly what it skipped: `312 hunks → 74 reviewable (238 filtered: lockfiles, generated, formatting)`.
30
31
-**Deterministic detectors** — commented-out code, removed-but-still-used declarations, and your own regex rules. These run before the model, cost nothing, and are the findings you can trust unconditionally.
31
32
-**Security, bug, performance and maintainability review** by a local model
33
+
-**Review standards as markdown** — commit your team's own rules to `.diffmind/rules/`, scoped by path. Prose the model reads, versioned next to the code it governs.
32
34
-**Ticket-aware review** — check the diff actually implements the acceptance criteria (`--ticket`)
33
35
-**Suppressions** — inline `// diffmind-ignore` comments and a project baseline, so one false positive doesn't get the whole gate deleted
34
36
-**SARIF output** — inline PR annotations via GitHub Code Scanning, no bot account or token
35
37
-**Pluggable backends** — the bundled GGUF, or your own Ollama / vLLM / LM Studio endpoint
36
38
-**Daemon mode** — keep the model resident so reviews are near-instant
37
39
-**Local RAG** — feeds the model the *enclosing function* of each hunk, not just the diff
38
40
-**Reproducible** — greedy decoding with a fixed seed: the same diff always reviews the same way
39
-
-**Interactive TUI** (`--tui`), JSON / Markdown output, and a proper CI gate
41
+
-**Reviewer's cockpit** (`--tui`) — analyses on launch, shows the hunk and context behind each finding, and records accept / dismiss / wrong so the signal-to-noise ratio is measured rather than guessed
42
+
- JSON / Markdown output, and a proper CI gate
40
43
41
44
---
42
45
@@ -53,7 +56,7 @@ Auto-detects your OS and CPU architecture, verifies the SHA-256 checksum, and in
53
56
Pin a specific version — note that the variable goes on the **`bash`** side of the pipe, not the `curl` side:
@@ -89,11 +92,14 @@ diffmind # review this branch against the repo's default branc
89
92
90
93
`--branch` is no longer assumed to be `main`: diffmind reads the repository's default branch from `origin/HEAD` and falls back to whichever of `main`/`master`/`develop`/`trunk` actually exists.
91
94
95
+
A bare `a..b` argument is recognised as a revision range without needing `--range`. The detection is strict — both endpoints must resolve as revisions and the string must not name an existing path — so `diffmind ../lib` and a file genuinely called `a..b` are still treated as paths. Paths after a range narrow it: `diffmind v1.2.0..HEAD src/api/`.
96
+
92
97
```bash
93
98
diffmind --last # just the last commit
94
99
diffmind --staged # just what's staged
100
+
diffmind v1.2.0..HEAD # an explicit revision range
95
101
diffmind src/auth/ # just these paths
96
-
diffmind --tui #interactive browser
102
+
diffmind --tui #the reviewer's cockpit
97
103
```
98
104
99
105
---
@@ -150,6 +156,7 @@ Findings carry a stable rule ID, shown in the output, so you can silence exactly
150
156
|`DM002`| A declaration was removed but is still referenced |
151
157
|`DM900.<category>`| A model-authored finding of that category |
152
158
|`custom.<slug>`| One of your `.diffmind/rules.toml` rules |
159
+
|`rulebook.<id>`| A violation of one of your `.diffmind/rules/*.md`|
153
160
154
161
### Inline
155
162
@@ -183,7 +190,7 @@ Commit `.diffmind/baseline.json`. Future runs report only new issues. The baseli
183
190
### GitHub Action
184
191
185
192
```yaml
186
-
- uses: thinkgrid-labs/diffmind@v0.8.0
193
+
- uses: thinkgrid-labs/diffmind@v0.9.0
187
194
with:
188
195
model: 1.5b
189
196
fail-on: high
@@ -192,7 +199,7 @@ Commit `.diffmind/baseline.json`. Future runs report only new issues. The baseli
192
199
That caches the model, installs the binary, reviews the PR diff, and uploads SARIF so findings appear inline on the diff. For a PR comment instead:
193
200
194
201
```yaml
195
-
- uses: thinkgrid-labs/diffmind@v0.8.0
202
+
- uses: thinkgrid-labs/diffmind@v0.9.0
196
203
with:
197
204
format: markdown
198
205
comment: true
@@ -231,13 +238,83 @@ Or via [pre-commit](https://pre-commit.com):
diffmind stats # cost and signal over recorded runs
446
+
diffmind stats --clear # drop run snapshots (verdicts are kept)
321
447
diffmind cache show # cache location and size
322
448
diffmind cache clear
323
449
```
@@ -335,6 +461,8 @@ Commands:
335
461
describe Generate a PR title and description
336
462
commit Suggest a conventional commit message
337
463
baseline Record current findings as accepted
464
+
rules Manage the prose rule sets in .diffmind/rules/
465
+
stats Findings, cost and accept/wrong ratio over recorded runs
338
466
install-hooks Install git hooks
339
467
serve Keep the model resident between runs
340
468
cache Inspect or clear the review cache
@@ -345,6 +473,7 @@ Options:
345
473
-l, --last Review the last commit only
346
474
--staged Review staged changes only
347
475
--stdin Read the diff from stdin
476
+
--range <RANGE> Review an explicit revision range, e.g. v1.2.0..HEAD
348
477
-t, --tui Launch the interactive TUI
349
478
--ticket <FILE_OR_TEXT> Acceptance criteria to check against
350
479
--min-severity <LEVEL> Minimum severity to report [default: low]
@@ -371,13 +500,14 @@ Options:
371
500
## How It Works
372
501
373
502
1. **Parse** — the diff is parsed once into typed per-file hunks with real pre/post-image line numbers.
374
-
2. **Deterministic detectors** — commented-out code, removed-but-used declarations, and your regex rules. No model involved.
375
-
3. **Context** — the enclosing function of each hunk (plus definitions of referenced symbols) is pulled from `.diffmind/symbols.json`.
376
-
4. **Triage** — on large diffs, a cheap first pass decides which files carry real risk.
377
-
5. **Chunked inference** — chunks are sized to the backend's *actual* context window, read from the GGUF metadata.
378
-
6. **Constrained decoding** — the sampler consults a JSON state machine before committing each token, so the model cannot emit a preamble, an unbalanced brace, or a truncated string. Output that hits the token cap is repaired rather than discarded.
379
-
7. **Anchoring** — findings pointing at a file not in the diff are dropped; off-by-N line numbers snap to the nearest changed line.
380
-
8. **Suppression** — inline directives, the baseline, and `--min-confidence` are applied, then results are deduplicated and sorted.
503
+
2. **Pre-filter** — lockfiles, `linguist-generated` paths, files carrying a `@generated` banner, minified bundles, assets, snapshots, your `ignore` globs, and hunks that only change whitespace are dropped. Costs nothing, typically removes most of a real branch, and the counts are reported rather than silently applied. Whitespace inside a string literal counts as content, and indentation is never dismissed in Python or YAML.
504
+
3. **Deterministic detectors** — commented-out code, removed-but-used declarations, and your regex rules. No model involved.
505
+
4. **Context** — the enclosing function of each hunk (plus definitions of referenced symbols) is pulled from `.diffmind/symbols.json`, assembled per chunk so one file's edit does not invalidate another's cached result.
506
+
5. **Triage** — on large diffs, a cheap first pass decides which files carry real risk.
507
+
6. **Review units** — hunks are grouped into regions of a file rather than cut wherever a line budget ran out, so related hunks are read together and an edit in one function only re-reviews that function. Units are sized to the backend's *actual* context window, read from the GGUF metadata.
508
+
7. **Constrained decoding** — the sampler consults a JSON state machine before committing each token, so the model cannot emit a preamble, an unbalanced brace, or a truncated string. Output that hits the token cap is repaired rather than discarded.
509
+
8. **Anchoring** — findings pointing at a file not in the diff are dropped; off-by-N line numbers snap to the nearest changed line.
510
+
9. **Suppression** — inline directives, the baseline, and `--min-confidence` are applied, then results are deduplicated and sorted.
0 commit comments