Push PR
Commit, push, and open a pull request whose body is adapted from the real diff
rather than copied from the template.
Migrated from .claude/commands/push-pr.md under ADR-064, which makes skills the
single user-invocable surface. The scoped allowed-tools grant, the
identity-hardened python3 -I form, and both vendor-portability declarations
carry over unchanged: they are the security contract, not formatting.
Triggers
push and open a PR, open a pull request, push this branch,
commit and push
Context
- Current git status: !
git status
- Current git diff (staged and unstaged changes): !
git diff HEAD
- Current branch: !
git branch --show-current
Process
Based on the above changes:
Create a new branch if on main.
- Determine the type of change that maps to a conventional commit type
followed by a 3-5 word description (for example,
fix/parser-log-enrichment).
Push the branch to origin.
Read @.github/PULL_REQUEST_TEMPLATE.md
Run the secure path allocator:
python3 -I "${COPILOT_PLUGIN_ROOT:-${CLAUDE_PLUGIN_ROOT:-.claude}}/skills/github/scripts/pr/new_pr.py" --prepare-body-file
- Copy the returned path exactly. Do not store it in a shell variable because
each tool call runs in a fresh shell.
- Use the Edit tool to replace
<!-- replace with PR body --> in that exact
file with the adapted template.
- Fill in all sections with actual change information from git diff
- Replace placeholder comments with substantive content
- Check appropriate Type of Change boxes based on actual changes
- List specific files changed, test coverage added, security impacts
- Do NOT leave template comments like
<!-- Brief description --> unfilled
- Do NOT copy the template verbatim - adapt every section to your changes
- Include an
## Acceptance criteria heading with - [ ] or * [ ] bullets. The Validate Spec Coverage job reads these from the PR body, not the linked issue. Any unchecked box makes the signal report FAIL, and that FAIL does not block the merge, so check a box only once the criterion is actually met. Numbered criteria are not recognized.
Create a pull request using the new_pr skill script:
python3 -I "${COPILOT_PLUGIN_ROOT:-${CLAUDE_PLUGIN_ROOT:-.claude}}/skills/github/scripts/pr/new_pr.py" --title "<conventional commit title>" --body-file ".agents/scratch/pr-body-<returned-uuid>.md"
- Title MUST follow conventional commit format (e.g.,
feat: Add feature, fix(auth): Resolve bug)
- Body SHOULD include GitHub issue linking keywords to auto-close issues:
Closes #123: auto-closes issue when PR merges
Fixes #456: auto-fixes issue when PR merges
Resolves #789: auto-resolves issue when PR merges
- Ensure PR template sections are completed
You have the capability to call multiple tools in a single response. You MUST do all of the above in a single message. Do not use any other tools or do anything else. Do not send any other text or messages besides these tool calls.
Verification
Anti-Patterns
| Avoid |
Why |
Instead |
| Storing the allocator path in a shell variable |
Each tool call runs a fresh shell, so the variable is empty on the next call and the body lands nowhere |
Copy the returned path literally into the next call |
| Copying the template verbatim |
Ships placeholder comments as the PR description, and the spec-coverage job reads them |
Adapt every section from the diff |
| Numbered acceptance criteria |
The Validate Spec Coverage job reads - [ ] and * [ ] only, so numbered items are invisible to it |
Use checkbox bullets |
| Checking a criterion box before it is met |
The signal reports a pass the PR does not have, and the FAIL it should have shown does not block merge |
Check a box only once the criterion holds |
Widening the allowed-tools grant to bare Bash |
Removes the CWE-78 argument scoping that makes this skill safe to auto-approve |
Add a specific scoped entry |
Extension Points
- Other forges. Steps 4 and 5 call
new_pr.py. A non-GitHub forge swaps that
helper; the template-adaptation rules in step 4 are forge-independent.
- Template changes. Step 4's section list follows the repository PR
template read in step 3. When that template gains a parsed section, add it to
step 4 and to the Verification list together.
- Branch naming. Step 1's conventional-type mapping is the repository
convention; a project with a different scheme changes that sub-step alone.
1---2name: push-pr3description: Commit the working tree, push the branch, and open a pull request with the repository template filled in from the real diff. Use when you say `push and open a PR`, `open a pull request`, or `push this branch`. Do NOT use to run the pre-ship review gates (use ship), and do NOT use to validate PR metadata alone (use validate-pr-description).4license: MIT5---67# Push PR89Commit, push, and open a pull request whose body is adapted from the real diff10rather than copied from the template.1112Migrated from `.claude/commands/push-pr.md` under ADR-064, which makes skills the13single user-invocable surface. The scoped `allowed-tools` grant, the14identity-hardened `python3 -I` form, and both vendor-portability declarations15carry over unchanged: they are the security contract, not formatting.1617## Triggers1819`push and open a PR`, `open a pull request`, `push this branch`,20`commit and push`2122## Context2324- Current git status: !`git status`25- Current git diff (staged and unstaged changes): !`git diff HEAD`26- Current branch: !`git branch --show-current`2728## Process2930Based on the above changes:31321. Create a new branch if on main.33 1. Determine the type of change that maps to a conventional commit type34 followed by a 3-5 word description (for example, `fix/parser-log-enrichment`).352. Push the branch to origin.363. Read @.github/PULL_REQUEST_TEMPLATE.md374. Run the secure path allocator:3839 ```bash40 python3 -I "${COPILOT_PLUGIN_ROOT:-${CLAUDE_PLUGIN_ROOT:-.claude}}/skills/github/scripts/pr/new_pr.py" --prepare-body-file41 ```4243 - Copy the returned path exactly. Do not store it in a shell variable because44 each tool call runs in a fresh shell.45 - Use the Edit tool to replace `<!-- replace with PR body -->` in that exact46 file with the adapted template.47 - **Fill in** all sections with actual change information from git diff48 - **Replace** placeholder comments with substantive content49 - **Check** appropriate Type of Change boxes based on actual changes50 - **List** specific files changed, test coverage added, security impacts51 - **Do NOT** leave template comments like `<!-- Brief description -->` unfilled52 - **Do NOT** copy the template verbatim - adapt every section to your changes53 - **Include** an `## Acceptance criteria` heading with `- [ ]` or `* [ ]` bullets. The Validate Spec Coverage job reads these from the PR body, not the linked issue. Any unchecked box makes the signal report FAIL, and that FAIL does not block the merge, so check a box only once the criterion is actually met. Numbered criteria are not recognized.545. Create a pull request using the new_pr skill script:5556 <!-- vendor-portability: declared. This skill reads the consumer's57 `.github/PULL_REQUEST_TEMPLATE.md` and writes the consumer's58 `.agents/scratch/` body file. It resolves the helper from the installed59 Copilot or Claude plugin root. The `.claude` fallback is only for this60 repository's self-hosted source checkout; `scripts/pr/` is inside the61 shipped github skill, not the upstream-only top-level scripts/ tree.62 Issue #4764. -->6364 ```bash65 python3 -I "${COPILOT_PLUGIN_ROOT:-${CLAUDE_PLUGIN_ROOT:-.claude}}/skills/github/scripts/pr/new_pr.py" --title "<conventional commit title>" --body-file ".agents/scratch/pr-body-<returned-uuid>.md"66 ```6768- Title MUST follow conventional commit format (e.g., `feat: Add feature`, `fix(auth): Resolve bug`)69- Body SHOULD include GitHub issue linking keywords to auto-close issues:70 - `Closes #123`: auto-closes issue when PR merges71 - `Fixes #456`: auto-fixes issue when PR merges72 - `Resolves #789`: auto-resolves issue when PR merges73- Ensure PR template sections are completed7475You have the capability to call multiple tools in a single response. You MUST do all of the above in a single message. Do not use any other tools or do anything else. Do not send any other text or messages besides these tool calls.7677## Verification7879- [ ] Branch created off main when the working branch was main, never a push to main80- [ ] Title follows conventional commit format81- [ ] Body written into the allocator's returned path, copied exactly, never through a shell variable82- [ ] Every template section adapted from the real diff, with no placeholder comment left in83- [ ] An `## Acceptance criteria` heading present with `- [ ]` bullets, checked only where met84- [ ] Issue-linking keyword present, and a closing keyword used only when the diff delivers what the issue asks8586## Anti-Patterns8788| Avoid | Why | Instead |89|-------|-----|---------|90| Storing the allocator path in a shell variable | Each tool call runs a fresh shell, so the variable is empty on the next call and the body lands nowhere | Copy the returned path literally into the next call |91| Copying the template verbatim | Ships placeholder comments as the PR description, and the spec-coverage job reads them | Adapt every section from the diff |92| Numbered acceptance criteria | The Validate Spec Coverage job reads `- [ ]` and `* [ ]` only, so numbered items are invisible to it | Use checkbox bullets |93| Checking a criterion box before it is met | The signal reports a pass the PR does not have, and the FAIL it should have shown does not block merge | Check a box only once the criterion holds |94| Widening the `allowed-tools` grant to bare `Bash` | Removes the CWE-78 argument scoping that makes this skill safe to auto-approve | Add a specific scoped entry |9596## Extension Points9798- **Other forges.** Steps 4 and 5 call `new_pr.py`. A non-GitHub forge swaps that99 helper; the template-adaptation rules in step 4 are forge-independent.100- **Template changes.** Step 4's section list follows the repository PR101 template read in step 3. When that template gains a parsed section, add it to102 step 4 and to the Verification list together.103- **Branch naming.** Step 1's conventional-type mapping is the repository104 convention; a project with a different scheme changes that sub-step alone.105106<!-- vendor-portability: .agents/scratch is created in the consumer workspace107for one-run PR body files. It is not an upstream repository dependency. -->