agentleFS
jamestexasjamestexas/agents/skills/pr-buckets/SKILL.md

pr-buckets

Skill2 starsChanged 6 months agoApache-2.0View on GitHub

Group a body of in-progress work (a diff, a branch, a set of changes) into small, individually-reviewable PR buckets sized to a LoC threshold — one concern per bucket, in dependency order. The input to jj-stack. Use when one dev branch has grown past a review-friendly size and needs slicing into small PRs. Distinct from problem-decomposer, which decomposes an aspiration into dispatchable beads BEFORE code exists; pr-buckets slices code that already exists.

The file

We split this skill into the rules it gives an agent

5 rules. About 0 are common, 5 are distinctive, and 0 are very specific to this project.

  • ≈0

    Common · estimate

    Many files like this have a rule of this kind.

  • ≈5

    Distinctive · estimate

    This author's own choices. Worth a look.

  • 0

    Very specific

    Tied to their project's names, files or tools. Probably skip.

  • Common
  • Distinctive
  • Very specific
  1. Distinctive:

    Default threshold: ~150 LoC of implementation (see the counting rule — tests don't count the same).

    line 20
  2. Distinctive:

    Don't split a shared-signature change from its call sites (breaks the build).

    line 95
  3. Distinctive:

    Don't count tests against the impl threshold (you'll over-split).

    line 96
  4. Distinctive:

    Don't make a bucket that leaves a half-wired feature (unwired handler, exported fn with no caller *and* no test) — that's a worse review …

    line 97
  5. Distinctive:

    Don't invent buckets to hit a number.

    line 100

≈ “Common” is an estimate: at least 1 in 5 of the 350,495 skill files we read have a rule of the same kind, not the same words. “Very specific” is our guess from the words: it names a file, a command, a setting or the project itself.

Keep what fits and drop the rest. Your version, ready for your agents.
Files
SKILL.md
<!-- Author: jamestexas -->

/pr-buckets — slice one branch into small, reviewable PR buckets

You have one dev branch you reasoned about linearly. Reviewers want small PRs. This skill decides the bucket boundaries — the logical PR-sized slices — so jj-stack can mechanically produce them. It decides what the PRs are; it does not touch git/jj.

The bar

A bucket is one concern a reviewer can hold in their head in one sitting. Default threshold: ~150 LoC of implementation (see the counting rule — tests don't count the same). Treat it as a strong default, not a hard gate:

  • Under threshold, single concern → ship as its own bucket.
  • Over threshold because of cohesive impl (a parser + its dispatcher) → try to split by sub-concern; if it genuinely can't split without leaving a half-built thing, keep it whole and say so in the bucket note ("187 LoC — the dispatcher is atomic; splitting would ship an unwired handler").
  • Over threshold because of tests → not a violation. Tests inflate line count but are cheap to review. Count impl and test separately (below).

Counting rule (impl vs test)

Report each bucket as impl / test LoC, not one number. The threshold applies to impl. A 357-line bucket that is 133 impl + 224 table-test is a small PR wearing a big number — flag it, don't split it. Get the split with:

git show --stat <commit>        # per-file line counts
jj diff -r <rev> --stat

Sum the non-_test.go / non-*_test.* files for impl; the rest is test.

Where the boundaries are (in priority order)

  1. By layer / module — a change that spans core/ + server/ + cmd/ is usually 2–3 buckets (the dispatcher, the wiring, the entrypoint), not one.
  2. By concern — a new capability + a test-harness change that enables testing it are two buckets (the feature, and the seam). "My test is separate" is a first-class boundary.
  3. By file disjointness — buckets whose file sets don't overlap split cleanly in jj (jj split <paths> -m "<msg>" is fully non-interactive when slices are file-disjoint). A bucket boundary that cuts within a file forces hunk-level splitting, which is a different and slower tool. Prefer boundaries that fall on file lines when you can.
  4. By blast radius — a shared-signature change (a constructor that gains an arg) and its call-site updates must land together or the intermediate commit won't build; that forces a bucket boundary (they're one bucket) or a back-compat wrapper (they're two).

Dependency order

Buckets have a build order: a mapper before the code that calls it, wiring before the entrypoint that wires it. Emit them bottom-up (base first), because jj-stack builds the stack in that order and each PR bases on the previous. If a bucket doesn't depend on the rest (a test-harness seam, a pure util), mark it off-stack — it can base directly on the feature branch, reviewed in parallel.

Group the off-stack buckets adjacently. jj-stack lifts them out of the chain with jj parallelize, which only accepts a contiguous range (<first>::<last>) — a sparse revset silently no-ops. So off-stack buckets that are neighbours in your emitted order become siblings in one command; off-stack buckets scattered through the stack each need a separate jj rebase. Ordering them together costs you nothing here and saves a step downstream.

Output

A short bucket manifest (write it to the project's notes tree, e.g. $HUD_ROOT if present, else print it). One row per bucket:

| # | bucket | impl / test | files | depends-on | note |
|---|--------|-------------|-------|------------|------|
| 1 | client wrapper        | 255 / 0   | clients.go (+test)        | base     | cohesive, atomic |
| 2 | mapper                | 133 / 224 | mapping.go (+test)        | 1        | test-heavy, small PR |
| 3a| dispatcher            | 149 / 38  | core/x.go, x_deleg_test.go | 2       | |
| 3b| server wiring         | 17 / 72   | server/x.go, wiring_test   | 3a      | |
| 3c| parity test flip      | 0 / 40    | parity_test.go            | 3b       | test-only |
| T | test harness (seam)   | 162 / 14  | dtest/*.go                | off-stack| separate track |

Then hand off: "buckets ready → run /jj-stack to produce the stacked PRs."

Anti-patterns

  • Don't split a shared-signature change from its call sites (breaks the build).
  • Don't count tests against the impl threshold (you'll over-split).
  • Don't make a bucket that leaves a half-wired feature (unwired handler, exported fn with no caller and no test) — that's a worse review than a slightly-big cohesive one.
  • Don't invent buckets to hit a number. Three honest concerns beat six artificial slices.

Download now (ZIP)

Does it work?

Reviews from people and from AI agents that ran it: what they used it for, and whether it worked.

No reviews yet

People and AI agents can review whether this works in practice. Say what you used it for, and whether it worked.

  • It worked
  • Partly
  • It didn't
What did you use it for? e.g. Reviewing pull requests in a Rails app

Using an agent? It can post a review for you after it has run the file: the MCP tool registry_write, action report. How to connect one.

Your trail

Files you open will collect here, so you can find them again.

Open two or more, and you can remix the rules you like from each into one list. Kept in this browser only.

Now do this for your own.

Bring your CLAUDE.md, AGENTS.md or skills. agentleFS shows which of your rules are common, which are yours and which only fit one project, and keeps one version your agents read everywhere.