Commit Repo
Streamlined commit flow for praxis-managed repos. One human gate only.
Repo Resolution
Resolve <repo-alias> to a git-managed path:
- If alias is the project root name (e.g.,
praxis): use CWD (the project root itself) - Otherwise: look up alias in CLAUDE.md → Alias Paths section, extract the
datapath
Example CLAUDE.md format:
## Alias Paths
- **nano-vc**: control `$PRAXIS_DIR/repos/nano-vc` | data `/home/mat/dev/nano-vc`
- **agent-skills**: control `$PRAXIS_DIR/repos/agent-skills` | data `/home/mat/dev/agent-skills`
The data value = the git repo path to commit in.
If alias not found, list available aliases from CLAUDE.md and exit.
Arguments
$ARGUMENTSfirst word = repo alias (required)--allflag: stage all modified files before committing (runsgit add -A)--yesflag: skip human confirmation gate — auto-approve the commit proposal- Without
--all: only commits what's already staged
Flow
CRITICAL: Each git command MUST be a separate Bash call. NEVER chain with &&, ||, or ;. This enables auto-approval via permission rules.
Phase 1: Recon (auto-approved, no human gate)
Run these as separate sequential Bash calls:
git -C <data-path> statusgit -C <data-path> diff --staged(if no--allflag) ORgit -C <data-path> diff(if--allflag, to show what will be staged)git -C <data-path> log --oneline -5
Phase 2: Analyze + Propose
From the recon output:
- List files that will be committed (staged files, or all modified if
--all) - Determine conventional commit
type(scope): descriptionper CLAUDE.md rules - Draft commit body:
What:bullets +Why:line
Phase 3: Propose + Confirm + Execute
- Output the proposal as text:
---
📦 Commit proposal for <alias> (<branch>)
Staged files:
- file1
- file2
Commit message:
type(scope): description
What:
- change 1
- change 2
Why: reason
If
--yesflag is set: skip confirmation, proceed directly to step 3. Otherwise — ⚠️ MANDATORY HUMAN GATE — use AskUserQuestion:- Question: "Proceed with commit? (y/n/edit)"
- If answer is empty/blank (known bug outside Plan Mode): fall back to inline text — output "Reply y to commit, n to abort, or edit to modify" and WAIT for user text reply
- If "n" or denied: abort, report "❌ Commit aborted"
- If "edit": ask what to change, revise, re-propose
- If "y" or approved: proceed to step 3
If
--all:git -C <data-path> add -ARun
git -C <data-path> commit -m "<message>"- If commit fails, report error and exit
Use HEREDOC for multi-line messages:
git -C <data-path> commit -m "$(cat <<'EOF'
subject line
What:
- change 1
- change 2
Why: reason
EOF
)"
- After successful commit:
git -C <data-path> log --oneline -1(auto-approved, verify success)
Report: ✅ Committed <short-hash> to <branch> in <alias>
Rules
- NEVER chain git commands — one command per Bash call
- NEVER add co-author tags — per CLAUDE.md
- NEVER push — user does this manually via IDE
- If no changes to commit, report and exit
- If alias not recognized, list available aliases and exit
Setup Requirements
1. CLAUDE.md Alias Paths
Your project CLAUDE.md must have an ## Alias Paths section with data paths pointing to git repos:
## Alias Paths
- **my-repo**: control `$PRAXIS_DIR/repos/my-repo` | data `/path/to/my-repo`
2. Permission Rules (settings.json)
Add auto-approve rules for read-only git commands on each repo path. Example for ~/.claude/settings.json:
"permissions": {
"allow": [
"Bash(git -C /path/to/repo status *)",
"Bash(git -C /path/to/repo status)",
"Bash(git -C /path/to/repo diff *)",
"Bash(git -C /path/to/repo diff)",
"Bash(git -C /path/to/repo log *)"
]
}
This keeps recon (Phase 1) zero-approval. The explicit AskUserQuestion in Phase 3 serves as the single human gate (do NOT rely on Bash permission prompts — they fail open inside skills, see Claude Code bug #18950/#25181).