LAB REF 2026.05 — 84 checks · offline-first · peer-reviewed logic

Ship notebooks that actually reproduce.

ReproGuard is a pre-flight inspection for Jupyter notebooks, Python scripts, and ML repos. It finds the risks that survive review — leakage, secrets in outputs, unpinned environments, out-of-order cells, unchecked agent tools — then gives you a score you can gate on.

terminal — reproguard lab machine · no network
# one install, no config required
$ pip install reproguard
$ reproguard scan .

Python 3.10+ runs entirely offline nothing leaves the machine

Apache-free · proprietary free-use Exit code 1 on fail 5 report formats
84 checks 7 risk classes 5 outputs: text, JSON, HTML, SARIF, GitLab 0 bytes uploaded — ever Filed as lab record · reproducible by design
Field notes — where notebooks break

Notebooks fail in ways linters don't look for

A notebook can be syntactically perfect, pass review, and still be impossible to rerun — or worse, leak data it was never supposed to see. These are the six failures we see most often in the lab.

Specimen LEAK001 · Leakage

Scaler fitted before the split

Test-set statistics bleed into training. The metric looks excellent and the model collapses in production. ReproGuard reads call order and flags it as critical.

fit_transform → train_test_split × wrong order
Specimen NB003 · Reproducibility

Cells run out of order

Execution counts that aren't monotonic mean the saved state doesn't match top-to-bottom code. Rerun it and you get different numbers, or a NameError.

Privacy · PII001

Keys and emails in outputs

Notebook outputs are committed alongside code. API keys, customer emails, and tracebacks stay in the file long after they scroll off screen.

Dependencies · DEP001

Unpinned, or not declared at all

No requirements file, or pip install pandas inside a cell. Both resolve to whatever is newest on install day.

Data · DATA001

Paths only you have

C:\Users\… and /Users/… work on exactly one machine. The next person opens the repo and stops.

GenAI · AGENT006 / LLMC003

Agents with unreviewed agency

Tools that shell out, model ids that aren't pinned, missing timeouts, prompts that interpolate untrusted input. Caught statically — no API keys required.

Agent → tool(shell=True) · model="gpt-4o" → pin the model, sandbox the tool

Lab principle

Silence over speculation

If ReproGuard can't parse a cell (non-Python kernel, IPython magic, corrupt JSON), it stays silent. A wrong finding costs more trust than a missing one.

Seven classes, one transparent score

Every finding carries a code, severity, confidence, the exact evidence line, and a fix you can apply. The score is a published penalty formula — severity weight times class weight — so you can recompute it by hand.

Class What it catches Range
Reproducibility Missing or unpinned dependency files, no random seeds, out-of-order execution, stale outputs, syntax errors, unpinned Docker base images Low → Critical
Data leakage Preprocessing before split, target-like feature columns, test data in fit calls, suspiciously high metrics, tracebacks and data dumps in output Low → Critical
Privacy & security Emails, phone and card numbers, AWS keys, hardcoded secrets, private keys, high-entropy credentials, credentials in URLs and connection URIs Low → Critical
Data dependency Local machine paths, referenced data files that don't exist, hardcoded paths in notebook output, large artifacts committed to git Medium → High
GenAI LLM client configuration, prompt injection bait, untrusted interpolation, LangGraph and CrewAI agent structure, tool agency, system-prompt leakage Low → Critical
Handoff readiness Missing objective, data source, assumptions, or metric documentation; uncommitted changes at scan time Low
Execution Notebook execution failures and kernel or dependency setup errors on a clean kernel run High → Critical

Scoring: penalty = Σ severity × (weight/20) × confidence · Score = 100 − penalty. Critical on any file caps the status at not ready.

Three steps to a gate you trust

Start permissive. Tighten as the debt comes down. The log tells you when a stricter gate is realistic.

  1. Scan anything — notebook, script, or entire repo

    Point it at one file or a directory. ReproGuard walks the tree once, picks up the nearest dependency files, and analyses each file notebook cell by cell, including the outputs. No config needed for the first run.

  2. Read the findings, not just the number

    Every issue is explainable: the code, why it triggered, the evidence line, and the fix. Suppress false positives per-path with checks.ignore rather than muting whole classes.

  3. Gate the pipeline without blocking progress

    --fail-under blocks on an absolute score. --baseline with --fail-new blocks only on regressions, so existing debt can be paid down gradually instead of all at once.

Try: reproguard scan . --baseline .reproguard/reproguard-report.json --fail-new 0 exit 1 only on new findings

Real reports, from real runs

Generated live · current release

These are not mockups. Each card below is a live reproguard scan report. Open the demo to filter by severity, expand any finding, and read the code that triggered it side-by-side with the source.

Built to live where your code already lives

ReproGuard has no server, no account, and no telemetry. It is a CLI that returns a meaningful exit code and speaks the formats your tooling already understands.

Where it runs

GitHub Actions and GitLab CI, a reusable composite action, a pre-commit hook, or a plain local run before you push. SARIF uploads straight into GitHub Code Scanning. Works on Linux, macOS, Windows.

What it emits

Color-coded terminal summary, JSON, standalone interactive HTML, SARIF 2.1.0, and a GitLab Code Quality report. Stream to stdout with -f json -o - and pipe to jq.

Deliberately conservative

Checks stay silent on code the tool cannot understand — non-Python kernels, IPython magics, corrupt notebooks. A finding you have to argue with is worse than no finding.

You stay in control

Tune severity penalties and class weights, disable individual checks, scope suppression by path and evidence regex, or add your own regex rules in .reproguard.yml.

No sign-up · no API key · runs on your machine

Scan your next notebook before someone else does

One pip install. Add a config only when a finding turns out to be wrong — and even then, per-path, not per-project.

pip install reproguard · reproguard scan . · Python 3.10+