AgentStack
Browse Sign in
Browse Why AgentStack Sell Docs
Sign in
SKILL verified MIT Self-run

Code Health

skill-ramboz-jig-code-health · by ramboz

>

No reviews yet
0 installs
30 views
0.0% view→install

Install

$ agentstack add skill-ramboz-jig-code-health

✓ scanned · ✓ verified, works with Claude Code, Cursor, and more.

Security review

✓ Passed

No issues found. Passed automated security review. · v0.1.0 How review works →

  • Prompt-injection patterns
  • Secret / credential exfiltration
  • Dangerous shell & filesystem operations
  • Untrusted network calls
  • Known-malicious package signatures

What it can access

  • Network access No
  • Filesystem access No
  • Shell / process execution Used
  • Environment & secrets No
  • Dynamic code execution No

From automated source analysis of v0.1.0. “Used” means the capability is present in the source — more access means more to trust, not that it’s unsafe.

View the full security report →

Verified badge

Passed review? Show it. Paste this badge into your README, it links to the public security report.

AgentStack Verified badge Links to your public security report.
[![AgentStack Verified](https://agentstack.voostack.com/badges/verified.svg)](https://agentstack.voostack.com/security/report/skill-ramboz-jig-code-health)

Reliability & compatibility

Security review passed
0 installs to date
no reviews yet
2mo ago

Declared compatibility

Claude CodeClaude Desktop

Compatibility is declared by the source manifest. End-to-end runtime verification is coming, see below.

Preview Execution monitoring

We're building live execution health for every listing: tool-call success rate, median latency, uptime, and last-checked timestamps, measured, not self-reported. It isn't live yet, so we don't show numbers we can't stand behind.

How agent discovery & health will work →
Are you the author of Code Health? Claim this listing to set pricing, connect Stripe payouts, and keep 70% of every sale.
Sign up to claim

About

> Spec 060 introduced code-health as the static-analysis sibling of > tdd-loop, under [ADR-0017](../../docs/decisions/adr-0017-scaffolded-code-health.md)'s > "detect the language → drive its blessed tools → normalize → degrade > gracefully" framing. Like tdd.py, the deterministic detection + > subprocess invocation live in health.py; this SKILL.md drives the > judgment layer. If another installed skill's description identifies it as > handling linting / static analysis / code quality, the Claude Code skill > router prefers it — the deferral is category-based.

What this skill does

Detects the project's ecosystem and runs its linter, normalizing the result so callers can branch deterministically. Ecosystem detection is table-driven — each ecosystem (Python, Node) is a data-structure entry, so adding a language is an entry, not a control-flow fork. Current scope: Python (ruff) + Node (eslint), each with advisory secondary signals.

  • A .jig/lint-command override always wins and **bypasses ecosystem

detection entirely** (honored verbatim — same semantics as tdd.py's .jig/test-command).

  • Otherwise detects the ecosystem by marker files (pyproject.toml / *.py

for Python; package.json for Node) and resolves its primary linter:

  • Pythonruff on PATHuvx ruffpipx run ruff (ephemeral),

invoked as ruff check --output-format=json .

  • Nodeeslint on PATHnpx eslint (ephemeral), invoked as

eslint --format json .

  • Parses the result into a tight summary — a findings count + the top

rule codes, not the raw dump (per spec 057's "tight envelope, not a transcript").

  • Adds an advisory dimension that is reported, not gating (it never

changes the exit code):

  • Python — complexity: an advisory ruff probe with

--select C901,PLR0911,PLR0912,PLR0913,PLR0915 surfaces a per-function complexity signal ("complexity: N function(s) over threshold; top: …").

  • Python — type checking: an advisory pyright --outputjson probe

resolves pyright on PATH, then uvx pyright, then pipx run pyright. Type diagnostics are summarized as a count + representative rules ("pyright: N type diagnostic(s); top: …"). If no type-checker resolves, it emits pyright: skipped (no type-checker) …. Like every advisory signal, it is reported, never gating.

  • Node — formatting: an advisory prettier --check probe surfaces

files that need formatting ("prettier: N file(s) need formatting").

  • Cross-ecosystem — duplication: an advisory probe (run for BOTH

Python and Node) reports copy/paste duplication. It is native-first (an explicit extension point for a future per-ecosystem native duplication tool — currently empty, since no jig ecosystem ships a distinct native detector), falls back to an ephemeral npx jscpd when npx is on PATH (the Node analogue of pipx run, works on any language, installs nothing), and otherwise emits duplication: skipped (no detector) — install a duplication tool or Node (npx jscpd) to enable. When it runs, the summary is a tight percentage + the top clones as file:line ("duplication: 4.2% (12 clones); top: foo.py:10, bar.py:88") — never the raw jscpd log. Like the other advisory signals it is reported, never gating (it cannot change the exit code).

  • Normalizes the primary linter's exit code:
  • 0 — clean (no findings)
  • 1 — findings exist (the linter ran and reported issues)
  • 2 — no linter resolvable, no recognized ecosystem, OR the resolved tool

failed to start

  • Degrades gracefully (AC4), never a stack trace:
  • no markers → exit 2 + "no recognized ecosystem (Python/Node) found

— set .jig/lint-command to run your linter".

  • one ecosystem, no resolvable linter → exit 2 + an

ecosystem-specific recommendation (ruff/pipx for Python; eslint/npx for Node).

  • mixed (2+ ecosystems) → exit 2 + a recommendation naming the

detected ecosystems and pointing at .jig/lint-command to disambiguate.

It installs nothinguvx / pipx / npx run the tools ephemerally only if those launchers are already on PATH.

Helper invocations

Two subcommands mirror tdd.py: detect reports which linter resolves, and check runs it.

Detect the linter

python3 "${CLAUDE_PLUGIN_ROOT}/skills/code-health/health.py" detect [target]
  • target defaults to . when omitted.
  • Stdout: the resolved primary linter name across ecosystems (ruff,

uvx ruff, pipx run ruff, eslint, or npx eslint).

  • Exit 2 with a recommendation on stderr if nothing resolves (no recognized

ecosystem, no resolvable linter, or a mixed project needing disambiguation).

Run the lint pass

python3 "${CLAUDE_PLUGIN_ROOT}/skills/code-health/health.py" check [target]
  • Auto-resolves the ecosystem's linter via the same logic as detect.
  • Prints a tight summary (count + top rule codes) to stdout, plus any

advisory lines (Python complexity / Python pyright / Node prettier / cross-ecosystem duplication) — advisory lines are reported but never change the exit code.

  • Exit code is normalized off the primary linter (0 clean / 1

findings / 2 no-linter) per the table above. Branch on it deterministically — exit 1 means inspect the summarized findings; exit 2 means the tool couldn't even start, no ecosystem was recognized, or a mixed project needs .jig/lint-command disambiguation — not "the code is clean".

Override the auto-detection

Create /.jig/lint-command with the first non-blank, non-comment line being the exact command to run. It is honored verbatim, takes priority over all auto-detection, and bypasses ecosystem detection entirely — the same semantics as tdd.py's .jig/test-command. Useful for a project whose linter isn't ruff/eslint (e.g. flake8 src or pylint mypkg), or to disambiguate a mixed Python+Node repo. (This is how jig's own CI is unaffected — jig commits a .jig/lint-command.)

When NOT to use

  • Running tests — that's /jig:tdd-loop (tdd.py). Static analysis and

the test loop are different cadences.

  • Security review — that's /jig:security-review; this skill is about

lint / style / correctness signals, not vulnerabilities.

  • Spec-compliance review of a finished slice — /jig:independent-review.
  • General PR craft review/jig:pr-review.
  • Pure-documentation edits that touch no code.

Relationship to other skills

health.py is the static-analysis sibling of tdd-loop's tdd.py — same detect → drive → normalize → degrade shape, same .jig/*-command override idiom, same 0 / 1 / 2 exit contract. Per [ADR-0002](../../docs/decisions/adr-0002-contracts-stays-deferred.md) the shared idioms (_read_text_safe / _custom_command_file / _parse_custom_command) are inline-mirrored, not extracted into a _common module — this is only the second helper of its kind, and the two have independent lifecycles. The deliberate duplication is noted in health.py's module docstring (exactly as tdd.py documents its own duplication of scaffold.py).

The code-health review pass (slice 060-05)

Beyond the health.py runner, jig wires a distinct code-health review pass into the post-implementation flow (alongside compliance / craft / arch). The layering ([ADR-0017](../../docs/decisions/adr-0017-scaffolded-code-health.md)): the spine runs the tool (health.py), and a read-only reviewer subagent judges its tight summary — rendering the judgment a static tool can't: is reported duplication within the [ADR-0002](../../docs/decisions/adr-0002-extract-helper-on-third-caller.md) inline-mirror budget (two callers may mirror; a third triggers an extract)? is a flagged complex function inherent or fixable? are the lint findings worth blocking on?

  • The reviewer never runs health.py. It is read-only

(Read/Glob/Grep, no Bash). The orchestrator / CI runs health.py, captures the tight summary, and feeds it into the prompt via review.py code-health … --summary-file (or stdin). The reviewer judges the summary, never raw logs.

  • The pass is GATED, not always-on. It runs only when a slice's

frontmatter declares code_health_review: true — exactly mirroring how arch_review: true gates the arch pass. Why gated: ADR-0017 flags the per-slice review cost (the spec 055/057 context-cost discipline — every pass adds orchestrator turns + a subagent), and recommends gating it like arch-review rather than spending it on every slice. The flag defaults off, so existing slices are unaffected; a slice author opts in when a change is duplication-/complexity-heavy enough to warrant the judgment.

  • Evidence + block rule. The verdict is recorded as

docs/specs/NNN-slug/reviews/slice-NN-code-health.md ([ADR-0014](../../docs/decisions/adr-0014-review-evidence-model.md) evidence model). [blocker]-tagged findings block the REVIEWED transition; [nit]-tagged findings become reconciliation-log items — the same rule as the craft/arch passes. workflow.py transition requires the code-health verdict for REVIEWED/DONE iff the flag is set. Query the flag with workflow.py code-health-review-needed .

See skills/spec-workflow/SKILL.md § "After implementation" for the full four-pass orchestration recipe.

Gotchas

  • **Scope is Python (ruff, + advisory complexity and pyright) and Node

(eslint, + advisory prettier --check), plus a cross-ecosystem advisory duplication signal (npx jscpd). The dedicated code-health reviewer pass (slice 060-05) is now live — see "The code-health review pass" above; the Tier-2 scaffold-the-floor work (slice 060-06) is DEFERRED**. An unrecognized ecosystem with no .jig/lint-command override degrades to a recommendation.

  • Advisory ≠ gating. The complexity and pyright (Python), prettier

(Node), and duplication (cross-ecosystem) signals are reported in the summary but never change the exit code — the exit code is driven solely by the primary linter (ruff / eslint). A clean ruff run with complexity or type findings still exits 0.

  • Duplication is honest about being unavailable. Unlike complexity /

prettier (which stay silent when their tool isn't present), the duplication probe emits duplication: skipped (no detector) … when neither a native tool nor npx is available — so a reader knows the dimension was not measured rather than measured clean. It writes jscpd's JSON report to a temp dir outside the project (read back, then removed) so it never pollutes your tree, and runs jscpd without --threshold so jscpd itself never exits non-zero (advisory, not gating).

  • The override path runs no advisory probes (including duplication) — it

honors .jig/lint-command verbatim without ecosystem detection, so jig's own dogfood CI (which sets an override) is unaffected.

  • Mixed repos degrade, they don't guess. If both pyproject.toml (or

*.py) and package.json are present, check exits 2 and asks you to set .jig/lint-command to disambiguate — it never picks one for you.

  • Exit 1 vs 2. Exit 1 means the linter ran and found issues —

inspect the summary. Exit 2 means no linter was resolvable, no ecosystem was recognized, a mixed project needs disambiguation, or the resolved tool failed to start (an environment issue) — don't conflate any of those with clean.

  • Ephemeral runs need a network/cache. uvx ruff / pipx run ruff /

uvx pyright / pipx run pyright / npx eslint / npx prettier / npx jscpd fetch the tool on first use. If neither the binary nor a launcher is present, the skill recommends (for the primary linter) or reports skipped (for pyright/duplication) rather than failing opaquely.

  • Tight summary, not the raw dump. check parses the linter's JSON into

a count + top codes; it does not echo the full tool output. Re-run the linter directly when you need every finding's location.

Source & license

This open-source skill is cataloged on AgentStack and links to its original source — we do not rehost the code.

Install and usage instructions live in the source repository linked above.

Reviews

No reviews yet, be the first.

Versions

  • v0.1.0 Imported from the upstream source.