commit-push-pr
Compare original and translation side by side
🇺🇸
Original
English🇨🇳
Translation
ChineseCommit, Push & PR Skill
Commit、Push与PR技能
Automates the git workflow of committing changes, pushing to GitHub, and opening a PR with intelligent handling of edge cases.
自动化提交变更、推送到GitHub并创建PR的Git工作流,同时智能处理各种边缘情况。
Required Reading
必读内容
Before executing, internalize the git workflow standards:
@.claude/rules/git_workflow.md
Key rules:
- Use Conventional Commits format:
type(scope): description - NEVER attribute Claude in commits or PRs (no co-author, no mentions)
- NEVER skip pre-commit hooks (no )
--no-verify
执行前,请熟悉Git工作流标准:
@.claude/rules/git_workflow.md
核心规则:
- 使用Conventional Commits格式:
type(scope): description - 绝对不要在提交或PR中提及Claude(不要添加共同作者,不要提及)
- 绝对不要跳过pre-commit钩子(不要使用)
--no-verify
Execution Workflow
执行流程
Step 1: Assess Git State
步骤1:评估Git状态
Run these commands to understand the current state:
bash
undefined运行以下命令了解当前状态:
bash
undefinedDetect the default branch (main, master, etc.)
检测默认分支(main、master等)
DEFAULT_BRANCH=$(git symbolic-ref refs/remotes/origin/HEAD 2>/dev/null | sed 's@^refs/remotes/origin/@@')
DEFAULT_BRANCH=$(git symbolic-ref refs/remotes/origin/HEAD 2>/dev/null | sed 's@^refs/remotes/origin/@@')
Fallback if symbolic-ref fails (e.g., shallow clone or missing HEAD)
当symbolic-ref失败时的备选方案(如浅克隆或缺少HEAD)
if [ -z "$DEFAULT_BRANCH" ]; then
DEFAULT_BRANCH=$(git remote show origin 2>/dev/null | grep 'HEAD branch' | awk '{print $NF}')
fi
if [ -z "$DEFAULT_BRANCH" ]; then
DEFAULT_BRANCH=$(git remote show origin 2>/dev/null | grep 'HEAD branch' | awk '{print $NF}')
fi
Final fallback to 'main' if detection fails
若检测失败,最终默认使用'main'
DEFAULT_BRANCH=${DEFAULT_BRANCH:-main}
DEFAULT_BRANCH=${DEFAULT_BRANCH:-main}
Get current branch
获取当前分支
BRANCH=$(git branch --show-current)
BRANCH=$(git branch --show-current)
Check for uncommitted changes
检查是否有未提交的变更
git status --porcelain
git status --porcelain
Check for unpushed commits (if branch has upstream)
检查是否有未推送的提交(如果分支有上游跟踪)
git log origin/$DEFAULT_BRANCH..HEAD --oneline 2>/dev/null || echo "No upstream or no commits ahead"
git log origin/$DEFAULT_BRANCH..HEAD --oneline 2>/dev/null || echo "无上游分支或无超前提交"
Check if branch has upstream tracking
检查分支是否有上游跟踪
git rev-parse --abbrev-ref @{upstream} 2>/dev/null || echo "No upstream"
Determine the state:
- `HAS_CHANGES`: Are there uncommitted changes (staged, unstaged, or untracked)?
- `HAS_UNPUSHED`: Are there commits ahead of origin/$DEFAULT_BRANCH?
- `ON_DEFAULT_BRANCH`: Is current branch the default branch ($DEFAULT_BRANCH)?
- `HAS_UPSTREAM`: Does the branch track a remote?git rev-parse --abbrev-ref @{upstream} 2>/dev/null || echo "无上游分支"
确定当前状态:
- `HAS_CHANGES`:是否存在未提交的变更(已暂存、未暂存或未跟踪文件)?
- `HAS_UNPUSHED`:是否有超前于origin/$DEFAULT_BRANCH的提交?
- `ON_DEFAULT_BRANCH`:当前分支是否为默认分支($DEFAULT_BRANCH)?
- `HAS_UPSTREAM`:分支是否跟踪远程分支?Step 2: Handle "Nothing to Do" Case
步骤2:处理“无操作可执行”场景
If :
!HAS_CHANGES && !HAS_UNPUSHEDInform user: "No changes to commit and no unpushed commits. Nothing to do."
Exit gracefully.如果:
!HAS_CHANGES && !HAS_UNPUSHED告知用户:"没有需要提交的变更,也没有未推送的提交。无需执行任何操作。"
优雅退出。Step 3: Handle "No Changes But Unpushed Commits" Case
步骤3:处理“无变更但有未推送提交”场景
If :
!HAS_CHANGES && HAS_UNPUSHED- Check if PR already exists:
bash
gh pr list --head "$(git branch --show-current)" --json number,url,title-
If PR exists:
- Offer to push updates to the existing PR
- Report the PR URL
-
If no PR:
- Offer to push and create a new PR
- Proceed to Step 7
如果:
!HAS_CHANGES && HAS_UNPUSHED- 检查PR是否已存在:
bash
gh pr list --head "$(git branch --show-current)" --json number,url,title-
若PR已存在:
- 提供将更新推送到现有PR的选项
- 告知PR的URL
-
若PR不存在:
- 提供推送并创建新PR的选项
- 继续执行步骤7
Step 4: Branch Management (if HAS_CHANGES)
步骤4:分支管理(若存在未提交变更)
If on default branch ($DEFAULT_BRANCH):
- Inform user that changes need to go on a feature branch
- Stage changes first to analyze them:
bash
git add -A
git diff --staged --stat-
Generate a conventional commit message based on the changes (see Step 5)
-
Derive branch name from commit message:
- →
feat(cli): add project listfeat-cli-add-project-list - →
fix: resolve memory leakfix-resolve-memory-leak - Rules: lowercase, replace spaces/special chars with hyphens, max 50 chars
-
Create and checkout the new branch:
bash
git checkout -b <branch-name>If already on feature branch:
- Continue with the existing branch
- Check if PR exists for context
若当前在默认分支($DEFAULT_BRANCH):
- 告知用户变更需要提交到特性分支
- 先暂存变更以进行分析:
bash
git add -A
git diff --staged --stat-
根据变更生成符合规范的提交信息(见步骤5)
-
从提交信息派生分支名称:
- →
feat(cli): add project listfeat-cli-add-project-list - →
fix: resolve memory leakfix-resolve-memory-leak - 规则:小写,将空格/特殊字符替换为连字符,最长50个字符
-
创建并切换到新分支:
bash
git checkout -b <branch-name>若当前已在特性分支:
- 继续使用现有分支
- 检查是否存在相关PR以获取上下文
Step 5: Stage Changes and Generate Commit Message
步骤5:暂存变更并生成提交信息
- Stage all changes:
bash
git add -A- Analyze the staged changes:
bash
git diff --staged --stat
git diff --staged-
Generate a conventional commit message based on:
- Files changed (infer scope from directory)
- Nature of changes (feat/fix/refactor/docs/test/chore)
- Summarize the "why" not just the "what"
-
Present the commit message to the user. Example format:
Proposed commit message:
feat(cli): add project listing command
Adds a new 'lf project list' command that displays all projects
in the current workspace with their status.
Do you want to use this message, modify it, or provide your own?- 暂存所有变更:
bash
git add -A- 分析已暂存的变更:
bash
git diff --staged --stat
git diff --staged-
根据以下内容生成符合规范的提交信息:
- 变更的文件(从目录推断范围)
- 变更类型(feat/fix/refactor/docs/test/chore)
- 总结变更的“原因”而非仅“内容”
-
向用户展示提交信息示例:
建议的提交信息:
feat(cli): add project listing command
Adds a new 'lf project list' command that displays all projects
in the current workspace with their status.
是否使用此信息、修改它,还是自行提供?Step 5.5: Quality Check
步骤5.5:质量检查
Skip if: flag was passed.
--quickRun quality checks on staged changes before committing.
若传入--quick参数则跳过此步骤
在提交前对已暂存的变更执行质量检查。
1. Auto-fix trivial issues (no prompt needed)
1. 自动修复小问题(无需提示)
Search for and remove debug statements:
bash
undefined查找并移除调试语句:
bash
undefinedFind files with debug statements
查找包含调试语句的文件
git diff --staged --name-only | xargs grep -l -E "(console.(log|debug|info)|debugger|print()" 2>/dev/null
For each file found:
- Remove `console.log(...)`, `console.debug(...)`, `console.info(...)` statements
- Remove `debugger;` statements
- Remove `print(...)` statements (Python)
- Re-stage the file after fixes
Report: "Auto-fixed: Removed N debug statements from M files"git diff --staged --name-only | xargs grep -l -E "(console.(log|debug|info)|debugger|print()" 2>/dev/null
对每个找到的文件:
- 移除`console.log(...)`、`console.debug(...)`、`console.info(...)`语句
- 移除`debugger;`语句
- 移除`print(...)`语句(Python)
- 修复后重新暂存文件
告知用户:"自动修复:从M个文件中移除了N条调试语句"2. Check for issues requiring attention
2. 检查需要关注的问题
Scan staged diff for:
| Issue | Severity | Action |
|---|---|---|
| Hardcoded secrets (API keys, passwords) | BLOCK | Cannot auto-fix - user must remove |
Command injection ( | BLOCK | Cannot auto-fix - user must refactor |
| Empty catch/except blocks | PROPOSE | Suggest adding error logging |
| Duplicate code patterns | PROPOSE | Suggest extraction |
| Unused imports | PROPOSE | Suggest removal |
| TODO/FIXME comments | WARN | Note but allow proceed |
扫描已暂存的变更以查找:
| 问题 | 严重程度 | 操作 |
|---|---|---|
| 硬编码密钥(API密钥、密码) | 阻止 | 无法自动修复 - 用户必须手动移除 |
命令注入( | 阻止 | 无法自动修复 - 用户必须重构 |
| 空的catch/except块 | 建议 | 建议添加错误日志 |
| 重复代码模式 | 建议 | 建议提取重构 |
| 未使用的导入 | 建议 | 建议移除 |
| TODO/FIXME注释 | 警告 | 仅提示但允许继续 |
3. Handle blocking issues
3. 处理阻止级问题
If BLOCK issues found:
- List each issue with file:line reference
- Stop the workflow
- User must fix manually and re-run
若发现阻止级问题:
- 列出每个问题的文件和行号
- 终止工作流
- 用户必须手动修复后重新运行
4. Handle proposable fixes
4. 处理建议修复的问题
For each PROPOSE issue:
- Show: file, line, problem, suggested fix
- Ask: "Apply this fix? (y/n/all/skip)"
- If approved: apply edit, re-stage
- If skipped: continue without fix
对每个建议修复的问题:
- 展示:文件、行号、问题、建议修复方案
- 询问:"是否应用此修复?(y/n/all/skip)"
- 若批准:应用修改并重新暂存
- 若跳过:不修复继续执行
5. Handle warnings
5. 处理警告级问题
For WARN issues:
- Display summary
- Continue without blocking
对警告级问题:
- 显示摘要
- 不阻止继续执行
Step 6: Create the Commit
步骤6:创建提交
Create the commit with the approved message:
bash
git commit -m "$(cat <<'EOF'
type(scope): short description
Optional longer description explaining the change.
EOF
)"Important:
- Use HEREDOC for multi-line messages
- Never add co-author or Claude attribution
- Let pre-commit hooks run (never use )
--no-verify
If commit fails due to pre-commit hook:
- Report the failure to the user
- Show the hook output
- Do NOT retry with
--no-verify - Ask user how to proceed (fix issues or abort)
使用已确认的信息创建提交:
bash
git commit -m "$(cat <<'EOF'
type(scope): short description
Optional longer description explaining the change.
EOF
)"重要提示:
- 对多行信息使用HEREDOC格式
- 绝对不要添加共同作者或提及Claude
- 让pre-commit钩子正常运行(绝对不要使用)
--no-verify
若提交因pre-commit钩子失败:
- 向用户报告失败
- 展示钩子的输出
- 不要使用重试
--no-verify - 询问用户如何处理(修复问题或终止)
Step 7: Push to Remote
步骤7:推送到远程仓库
- Check if branch has upstream:
bash
git rev-parse --abbrev-ref @{upstream} 2>/dev/null- If no upstream, push with :
-u
bash
git push -u origin $(git branch --show-current)- If has upstream, regular push:
bash
git pushIf push fails due to conflicts:
- Inform user about the conflict
- Suggest: or
git pull --rebase origin $DEFAULT_BRANCHgit merge origin/$DEFAULT_BRANCH - Do NOT force push
- 检查分支是否有上游跟踪:
bash
git rev-parse --abbrev-ref @{upstream} 2>/dev/null- 若无上游分支,使用参数推送:
-u
bash
git push -u origin $(git branch --show-current)- 若已有上游分支,直接推送:
bash
git push若推送因冲突被拒绝:
- 告知用户存在冲突
- 建议执行:或
git pull --rebase origin $DEFAULT_BRANCHgit merge origin/$DEFAULT_BRANCH - 绝对不要强制推送
Step 8: Create or Report PR
步骤8:创建或报告PR
- Check if PR already exists:
bash
gh pr list --head "$(git branch --show-current)" --json number,url,title-
If PR exists:
- Report: "Changes pushed to existing PR: <URL>"
- Show PR title and number
-
If no PR exists:
- Generate PR title from commit message (first line)
- Generate PR body with summary of changes
- Create PR:
bash
gh pr create --title "type(scope): description" --body "$(cat <<'EOF'- 检查PR是否已存在:
bash
gh pr list --head "$(git branch --show-current)" --json number,url,title-
若PR已存在:
- 告知:"变更已推送到现有PR:<URL>"
- 展示PR的标题和编号
-
若PR不存在:
- 从提交信息生成PR标题(第一行)
- 生成包含变更摘要的PR正文
- 创建PR:
bash
gh pr create --title "type(scope): description" --body "$(cat <<'EOF'Summary
Summary
- Brief description of changes
- Brief description of changes
Changes
Changes
- List of key changes made
- List of key changes made
Test Plan
Test Plan
- How to verify these changes work EOF )"
4. Report the new PR URL to the user
---- How to verify these changes work EOF )"
4. 向用户告知新PR的URL
---Branch Name Generation
分支名称生成规则
Convert commit message to valid branch name:
| Input | Output |
|---|---|
| |
| |
| |
Algorithm:
- Take the commit message (first line only)
- Lowercase everything
- Remove the colon after type/scope
- Replace and
(with)- - Replace spaces and special characters with
- - Collapse multiple hyphens to single hyphen
- Trim to max 50 characters at word boundary
- Remove trailing hyphens
将提交信息转换为有效的分支名称:
| 输入 | 输出 |
|---|---|
| |
| |
| |
算法:
- 仅取提交信息的第一行
- 全部转换为小写
- 移除类型/范围后的冒号
- 将和
(替换为)- - 将空格和特殊字符替换为
- - 将多个连续的合并为一个
- - 在单词边界处截断至最长50个字符
- 移除末尾的
-
Error Handling
错误处理
| Error | Action |
|---|---|
| Pre-commit hook fails | Show output, ask user to fix, do NOT bypass |
| Push rejected (conflicts) | Suggest rebase/merge, do NOT force push |
| PR creation fails | Show error, suggest manual creation |
| Not a git repo | Inform user, exit |
| gh CLI not installed | Inform user how to install |
| Not authenticated to GitHub | Suggest |
| 错误 | 操作 |
|---|---|
| Pre-commit钩子执行失败 | 展示输出,让用户修复,绝对不要绕过 |
| 推送被拒绝(冲突) | 建议执行变基/合并,绝对不要强制推送 |
| PR创建失败 | 展示错误,建议手动创建 |
| 当前目录不是Git仓库 | 告知用户,退出 |
| 未安装gh CLI | 告知用户安装方法 |
| 未登录GitHub | 建议执行 |
Output Format
输出格式
On success, report:
Committed: feat(cli): add project list command
Branch: feat-cli-add-project-list-command
Pushed to: origin/feat-cli-add-project-list-command
PR: https://github.com/owner/repo/pull/123执行成功后,输出:
已提交:feat(cli): add project list command
分支:feat-cli-add-project-list-command
已推送到:origin/feat-cli-add-project-list-command
PR:https://github.com/owner/repo/pull/123Notes for the Agent
给Agent的注意事项
- Never mention Claude - No co-author lines, no "generated by Claude" in PR descriptions
- Respect hooks - Pre-commit hooks exist for a reason, never skip them
- Be informative - Tell the user what's happening at each step
- Handle errors gracefully - Don't leave the repo in a broken state
- Ask when uncertain - If the commit message isn't clear, ask the user
- Keep it simple - One commit per invocation, clear linear workflow
- 绝对不要提及Claude - 不要添加共同作者,不要在PR描述中出现“由Claude生成”的内容
- 尊重钩子 - Pre-commit钩子存在是有原因的,绝对不要跳过
- 信息透明 - 在每个步骤告知用户正在执行的操作
- 优雅处理错误 - 不要让仓库处于损坏状态
- 不确定时询问 - 若提交信息不明确,询问用户
- 保持简洁 - 每次调用只创建一个提交,使用清晰的线性工作流