- Dockerfile 100%
The /pr workflow section in the README still described the old pre-flight as a hard blocker — that contradicts the simplified behaviour now in skills/pr/SKILL.md and agents/pr-worker.md. Rewrite the four-step list to reflect that compose is always non-blocking on remote state, surface the "Open gate" as a separate fifth step so readers see where /push enforcement actually lives, and note that the existing-PR lookup is skipped when the branch isn't on the remote. |
||
|---|---|---|
| .claude | ||
| .claude-plugin | ||
| agents | ||
| claude-jail | ||
| skills | ||
| .gitignore | ||
| LICENSE | ||
| README.md | ||
conventional-commit
Disciplined Git workflow for Claude Code: Conventional Commits, atomic commits, typed branches, and linear history via rebase merge. Provides three skills that guide Claude through a strict commit/push/PR workflow instead of letting it improvise.
Install
Assuming you've already added the marketplace:
/plugin install conventional-commit@claudiomaradonna
Skills
/commit— local-only: stage and commit on a typed branch off an up-to-date base./push— publish: resolve the remote, confirm, push. Stops after the push; hands off to/pr./pr— open a pull/merge request: detect the provider, refuse to duplicate an existing PR, compose a Conventional-Commits-aligned title and motivation-focused body, and open viagh/glab/tea(or hand back a compare URL).
Each skill is a thin orchestrator. The actual workflow body lives in a dedicated subagent (agents/commit-worker.md, agents/push-worker.md, agents/pr-worker.md) so the procedure never enters the main session context — see Architecture below.
/commit workflow
- Pre-flight — resolve the base remote (no hardcoded
origin); then in parallel:git status, current branch, recent log,git fetch <base-remote>. If commit signing is enabled, also verify the configured key is usable before staging — try SSH-agent recovery first, then stop and ask the user (stop / fix / authorize unsigned for this single commit) rather than silently bypassing with-c commit.gpgsign=false. - Branch setup — never commit on
main/master; create a typed branch off an up-to-date base, or confirm the current dedicated branch is the right place. - Branch naming —
<type>/<short-kebab-description>where<type>is one of:feat,fix,sec,chore,docs,refactor,test,perf,ci,build. - Atomic grouping — propose a commit-by-commit split where each commit is a single logical, revertible unit; show the plan before staging.
- Conventional Commits —
<type>(<scope>): <description>with a mandatory body explaining why (unless the change is trivially obvious). Breaking changes use!plus aBREAKING CHANGE:footer. - Stage & commit — explicit staging (no
git add -A/git add .); when a single file's changes span multiple commits, split at hunk granularity via a patch-file flow rather than restructuring files. - Handoff — list the commits, point the user at
/pushto publish and then/prto open a PR/MR./commitnever pushes and never opens a PR.
/push workflow
- Resolve the remote — upstream of the current branch first; otherwise the single remote, or ask the user when there are several. Never assume
origin. - Confirm and push — show branch, target remote, commits to publish, and ask before pushing. Push with
-uif no upstream is set. - Handoff — list the commits just published, print a courtesy compare URL when the host matches a well-known pattern, and point the user at
/prto open a PR/MR./pushnever opens a PR.
/pr workflow
- Pre-flight — branch must not be
main/masterand must have commits ahead of the base. Remote state (no upstream, branch not on the remote, local ahead of remote tip) is reported as warnings on the proposal, never as a hard blocker — the title/body proposal is always composed and shown to the user, even before the branch is pushed. - Detect the provider — parse the remote URL: GitHub →
gh, GitLab →glab, Gitea/Forgejo →tea, Bitbucket / unknown → manual. Covers self-hosted via existing CLI logins or env vars (GITEA_SERVER_URL+GITEA_SERVER_TOKEN,GH_HOST+GH_TOKEN,GITLAB_HOST+GITLAB_TOKEN). - Check for an existing PR/MR — if one is already open for the branch, surface its URL and stop instead of creating a duplicate. Skipped when the branch isn't on the remote yet (nothing to duplicate).
- Offer the PR/MR — ask explicitly before opening one. If the user prefers to do it manually, or no CLI is available, hand back a ready-to-click compare URL plus the proposed title and body. PR body always states merge with rebase.
- Open gate — when the user approves opening, if the branch isn't yet on the remote
/prpoints at/pushand stops rather than auto-pushing. Once published, the open pass re-probesgit ls-remoteand only re-raisesneeds_pushif the branch was deleted in the meantime.
Architecture
Each skill (/commit, /push, /pr) is a thin orchestrator (~50 lines) that drives a two-pass exchange with a dedicated plugin-scoped subagent (commit-worker, push-worker, pr-worker):
- pass 1 — propose / resolve / compose: the orchestrator spawns the subagent in plan mode. The subagent performs pre-flight, gathers state, and returns a short human summary plus an opaque YAML plan. The full workflow body — hundreds of lines of rules and procedures — lives inside the subagent's isolated context and never enters the main session.
- user checkpoint: the orchestrator surfaces the human summary in the main session and asks the user (
AskUserQuestion) to approve, edit, or cancel. - pass 2 — execute / push / open: on approval, the orchestrator re-spawns the subagent in execute mode with the approved plan; the subagent carries out the actual state-changing work (staging + committing, pushing, opening the PR/MR) and returns a concise result summary.
The motivation is token-cost: the previous monolithic SKILL.md bodies (~16 KB across the three skills) used to load into the main session on each invocation and persist there for every subsequent turn. With the subagent split, the main session only ever holds the thin orchestrators and the short summary artifacts — the heavy workflow logic is paid only inside the subagent's ephemeral context and discarded when it terminates.
This means the plugin requires a Claude Code runtime that supports plugin-scoped subagents at <plugin-root>/agents/<name>.md.
Safety rules built in
/commitnever pushes./pushnever pushes without explicit user "yes" and never opens PRs./prnever opens a PR/MR without explicit user "yes".- Never
--no-verify, never blind--force/--force-with-lease, nevergit add -A. - Never silently disable commit signing — if the configured key (SSH/GPG/x509) isn't usable, recover when possible, otherwise stop and let the user choose;
-c commit.gpgsign=falseis per-commit and only on explicit user authorization. - Pre-commit / pre-push hook failure → fix and create a new commit, never bypass.
- Base branch behind its remote → rebase, never merge.
- Warn on staged files that look like secrets (
.env,credentials.*, private keys). - Never assume the remote is
origin; never assume the provider is GitHub.
Multi-branch changes
Handled interactively: when a change legitimately belongs on more than one branch, Claude asks the user whether to cherry-pick, split, or defer rather than picking a strategy on its own.
Optional: claude-jail companion image
If you run Claude inside claude-jail and want /pr to open PRs/MRs natively (instead of returning a compare URL), this plugin ships a Dockerfile at claude-jail/Dockerfile that layers gh / glab / tea on top of the claude-code image. All three blocks are commented out by default — uncomment only the providers you use, then build and run via --image:
podman build -t claude-code-pr -f claude-jail/Dockerfile .
claude --image claude-code-pr <directory>
If you install multiple plugins that ship their own companion image, you'll need to merge their RUN blocks into a single Dockerfile by hand — there is no automatic composition.
Conventions reference
- Conventional Commits 1.0.0
- Semantic Versioning — driven by commit types (
feat→ minor,fix→ patch,BREAKING CHANGE→ major)
License
BSD 3-Clause — see LICENSE.