Knows when a PR doesn't belong in your codebase.
Project description
VibeDiff
AI agents write code that compiles, passes tests, and feels completely foreign in your codebase. It works — but it doesn't fit. Your naming is snake_case, the PR is camelCase. Your project uses properties, the PR is full of getter/setter methods straight out of a Java textbook. The author committed 500 lines without changing a single AI-generated variable name.
VibeDiff learns how your project actually writes code, then tells you when a PR doesn't match.
What it catches
- Style drift — your codebase uses one set of conventions, the PR uses another
- Idiom contamination — AI bleeds patterns from other languages into your code (Java-style Python, Go-style error handling in JS, etc.)
- Raw AI dumps — 500 lines committed with zero human editing, generic variable names, TODO placeholders left in
How it works
VibeDiff runs 4 analyzers on every diff:
AI Detection (0-100) — heuristic signals that code was AI-generated:
- Comment patterns (restating code, section headers, excessive density)
- Naming patterns (verbose 4+ word names, uniform naming, no short vars)
- Burstiness (AI has uniform line complexity; humans vary wildly)
- Structural patterns (excessive
is Noneguards, broadexcept Exception)
Style Drift (0-100) — how much the diff deviates from your codebase conventions:
- Naming convention mismatch (camelCase in a snake_case codebase)
- Comment density deviation from baseline
- Function length drift (2x longer or 0.4x shorter than average)
- Import style mismatch (bare imports vs from-imports)
Run vibediff learn first to build a fingerprint of your codebase conventions.
Collaboration Quality (0-100) — signs the human didn't actually review the AI output:
- Unresolved TODO comments left in
- Generic variable names (data, result, output, value)
- Generic test names (test_function_1, test_method_2)
- Placeholder stubs (pass, ..., NotImplementedError)
- Uniform comment density across files (no human editing trace)
Idiom Contamination (0-100) — AI bleeding patterns from other languages:
- Java in Python: getter/setter methods, Interface/Abstract class naming
- Go in Python: error-return patterns (
return data, err) - C/C++ in Python:
== Noneinstead ofis None - JavaScript in Python: callback parameters
Install
pip install vibediff
Usage
# Review last commit
vibediff review HEAD~1
# Review a range
vibediff review main..feature
# Review a GitHub PR (requires gh CLI)
vibediff review --pr 42
# Learn your codebase conventions first (enables drift detection)
vibediff learn
# Skip drift analysis
vibediff review HEAD~1 --no-fingerprint
# JSON output (for CI pipelines)
vibediff review HEAD~1 --format json
# Markdown output (for PR comments)
vibediff review HEAD~1 --format md
Every diff gets a letter grade (A-F) synthesized from all 4 analyzers:
╭──────────────────────────────── VibeDiff ─────────────────────────────────╮
│ │
│ ████ 3 file(s) +180 -12 │
│ ██ ██ │
│ ██ ██ AI Detection █████████░░░░░░ 58 medium │
│ ██ ██ Style Drift ██████░░░░░░░░░ 42 medium │
│ ████ Collaboration ██████████░░░░░ 65 mixed │
│ Idiom Contamination ██████░░░░░░░░░ 40 medium │
│ │
╰──────────────────────────────────────────────────────────────────────────╯
──────────────── AI Detection 58/100 (medium) ─────────────────
restating_comments 4 comments that restate the code ███░░
verbose_names 3/5 functions have 4+ word names ██░░░
low_burstiness CV 0.31 (expected >0.6) ██░░░
────────────────── Style Drift 42/100 (medium) ────────────────
naming_convention expected snake_case, got camelCase ███░░
comment_density expected 8%, got 22% ██░░░
─────────────── Collaboration 65/100 (mixed) ──────────────────
unresolved_todos 3 TODO comments left in ██░░░
generic_names 4/12 variables have generic names ██░░░
──────────── Idiom Contamination 40/100 (medium) ──────────────
getter_setter 3 getter/setter methods [java] ███░░
error_return_pattern 4 Go-style error returns [go] ██░░░
GitHub Action
Add VibeDiff to your PR workflow:
# .github/workflows/vibediff.yml
name: VibeDiff
on:
pull_request:
jobs:
review:
runs-on: ubuntu-latest
permissions:
pull-requests: read
steps:
- uses: actions/checkout@v4
with:
fetch-depth: 0
- uses: doncarbon/VibeDiff@main
The action posts a markdown report to the PR's job summary. To enable style drift detection, commit a fingerprint and pass it:
- uses: doncarbon/VibeDiff@main
with:
fingerprint: .vibediff-cache/fingerprint.json
Author
License
MIT
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file vibediff-0.1.0.tar.gz.
File metadata
- Download URL: vibediff-0.1.0.tar.gz
- Upload date:
- Size: 23.3 kB
- Tags: Source
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.12.3
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
574baf5c01ab067d261eef3de780aecd929fc71c8ed1fe92195f4a14c8e86fa3
|
|
| MD5 |
1190738b82eca5d1abb17d286f266823
|
|
| BLAKE2b-256 |
b1314286ab6d5a4307e2743722dad4c4f401868f228d3b4febe3494d37c21145
|
File details
Details for the file vibediff-0.1.0-py3-none-any.whl.
File metadata
- Download URL: vibediff-0.1.0-py3-none-any.whl
- Upload date:
- Size: 20.5 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.12.3
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
5c59da7528e158e1d5e256acc79487e3b85d832d5506bb1e6f7a4de83f64845d
|
|
| MD5 |
68ed2ecaadffdbf134c518ec549dd184
|
|
| BLAKE2b-256 |
b215b9cd0f83abef93c5cbec54bbc980a0df694bb44566714ad00f16bd59215f
|