Repository navigation
What is cheatcheck?
cheatcheck reads a git diff and reports the shortcuts an AI coding agent takes to make a change look finished: deleted tests, skipped specs, weakened assertions, swallowed errors, disabled checks.
No model calls. No network. No API key. 16 rules, zero runtime dependencies.
npx cheatcheck --diff changes.patch
npx cheatcheck --base origin/mainExit code is 0 when clean, 1 when suspicious.
Install
npm install -g cheatcheck
# or
npx cheatcheck0.1.0
First release. cheatcheck reads a git diff and reports the shortcuts an AI coding agent takes to
make a change look finished: tests that disappeared, specs that stopped running, assertions that
became unfalsifiable, errors that stopped propagating, checks that were switched off.
Added
-
Zero-dependency diff parser (
src/diff.ts). Handles multi-file diffs, renames, binary files,
new/deleted files, and\ No newline at end of filemarkers. -
16 rules across five languages families (JS/TS, Python, Go, Rust, Java/Kotlin, .NET, Ruby):
Rule Severity Catches test-deletedcritical Net loss of test declarations in a test file test-file-deletedcritical A test file removed without a rename test-skippedcritical .skip,.only,xit,@pytest.mark.skip,t.Skip,#[ignore],@Disabledtest-ignoredcritical New ignore patterns or discovery changes that stop tests running mock-under-testcritical A test that mocks the module it is supposed to verify assertions-removedhigh Net loss of assertions assertion-weakenedhigh toBe/toEqualreplaced bytoBeTruthy/toBeDefinederror-swallowedhigh Empty catch {},except: pass, bare.catch(() => {})checks-disabledhigh Blanket @ts-nocheck,eslint-disable,# type: ignorewith no reasonconfig-loosenedhigh "strict": false,skipLibCheck,--passWithNoTests,continue-on-error: truesnapshot-blasthigh A snapshot file with a large one-way rewrite lint-suppressedmedium One-line suppressions with no reason given stub-implementationmedium not implemented,TODO: implement,return null; // stubmock-inflationmedium Three or more new mocks in one file test-ratiomedium 150+ lines of implementation and almost no test change type-escapelow Three or more new anycasts in production code -
Trust score. Per-rule multiplicative deduction, one charge per rule per diff, and a hard cap of
39 when any critical rule fires. Verdicts:PASS(90–100),REVIEW(70–89),RISKY(40–69),
FAIL(0–39). -
Diff sources. Working tree,
--staged,--base <ref>,--range <a>..<b>,--diff <file>,
and--stdin. -
Output formats. Human terminal output with colour and CJK-aware alignment,
--json,--md
(PR comment), and--format github(native workflow annotations). -
Bilingual messages. Every finding, rule name and explanation exists in English and Chinese.
--lang en|zhoverrides the locale. -
.cheatcheckrc.jsonwiththreshold,strict,ignore,ignoreRulesandlang. -
GitHub Action (
action.yml) and a self-checking workflow, both running the committeddist/
so no build step is required. -
Documentation.
README.md,README.zh-CN.md,docs/rules.md,CONTRIBUTING.md, and
generated terminal screenshots indocs/. -
Tests. 51 tests covering the parser, every rule (positive and near-miss), scoring, the CLI, and
documentation completeness.npm run verify:reposfetches the latest commit ofchalk,trpc,
vitest,hono,got,slugifyandp-limit; all must score 100.
Design notes
- Precision over recall. A suppression comment with a real reason (12+ characters) is treated as
engineering, not cheating. Only unjustified suppressions are reported. Suppression text inside a
string literal, regex or documentation snippet is ignored, so fixtures and code examples do not
produce findings. - No model, no network, no key, no telemetry. The CLI is a pure function from diff bytes to a
report. That makes it safe to run in CI and in a pre-commit hook. - Only the diff is inspected. Pre-existing problems are out of scope by design. The repository's
own release commit scores 100 withcheatcheck --range.
Full changelog: https://github.com/YKLovePython/cheatcheck/blob/main/CHANGELOG.md