SDK Pod PR Creation
SkillDev toolsGenerate PR descriptions for SDK pod packages following template and format rules. Use when creating an SDK pod PR or invoking /qv-sdk-pr-create.
Available today. Use it from your connected AI after setup.
No other account needed.
Connect ahel once, and every AI you use reads what you have installed.
Then ask your AI: use the SDK Pod PR Creation skill
What this skill tells your AI
The instructions your AI receives, as published by tetherto/qvac in .agents/skills/qv-sdk-pr-create/SKILL.md and read by ahel’s review.
Generate PR titles and descriptions for SDK pod packages, following the team's template and format rules.
When to use this skill
Applies to SDK pod packages whose paths are owned by .github/teams/sdk.json.
Use when:
- Creating a PR for any SDK pod package
- User asks to generate PR description
- User invokes
/qv-sdk-pr-create
Branch / remote preference
Preferred path for internal SDK work: push the head branch to the org repo (tetherto/qvac) and open a same-repo PR. Org-branch ready PRs get baseline CI without any fork trust gate. Heavy tiers still opt in via labels (test-e2e-smoke / test-e2e-full, addon stage labels, etc.). Prefer Ready for review over Draft when you want baseline checks to run (drafts run nothing until ready).
Fallback: personal-fork → org PRs still work, but a personal fork counts as external. Privileged CI needs a merge/release-team member to approve the fork-ci environment on each workflow run for the current head SHA; each new push re-prompts. Do not ask the PR author to self-approve fork-ci.
Resolve remotes from git remote -v:
- Org remote — URL contains
tetherto/qvac(often namedupstream, sometimesorigin) - Fork remote — contributor fork, if present (often named
originwhen org isupstream)
In command examples below, ORG_REMOTE / FORK_REMOTE / BRANCH are placeholders — substitute the resolved remote and branch names. Do not run those tokens literally.
Release PR branch naming (org-branch path)
publish-sdk.yml (and sibling publish workflows) run Release Merge Guard on
push to any release-* ref. The guard validates github.ref_name — the branch
that was pushed — not the PR base. It requires
release-<pkg>-x.y.z (three-part semver).
Consequences for release changelog / metadata PRs:
- Base (target) must be exactly
release-<pkg>-<x.y.z>(e.g.release-sdk-0.17.0). Short cuts likerelease-sdk-0.17fail the guard on merge/publish. If the cut is short-named, STOP and ask a repo admin to rename it to the three-part form before relying on publish (protected-branch rename needs admin). - Head (working branch) must not start with
release-when pushed to the org remote. Preferchore/<pkg>-<x.y.z>-changelog(e.g.chore/sdk-0.17.0-changelog). Names likerelease-sdk-0.17.0-changelogtrip Release Merge Guard on the helper push and can leave a failing check on that commit SHA. - GitHub cannot retarget a PR's head. To rename a bad head: push the same
commits under the new name, open a new PR, close the old one, delete the old
remote head. If the new PR still shows a stale Release Merge Guard fail on the
same SHA, push an empty
[skiplog]commit so checks reattach to a fresh SHA.
backmerge/release-<pkg>-<x.y.z> heads are fine — they do not match the
release-* push trigger.
Workflow
- Identify base and current branch — note whether the base is
mainor arelease-<pkg>-<x.y.z>branch. For release PRs, apply Release PR branch naming above (base three-part; head notrelease-*) - Resolve the head remote (prefer org remote; see above). Collect commits/diff from
<base>...<head-remote>/<branch>(or localHEADif not yet pushed) - Infer ticket, prefix, and tags from changes (see Inference Strategy)
- Only ask user for input when inference confidence is low
- Generate title:
TICKET prefix[tags]: subject - Fill template sections based on changes
- Validate tag requirements ([bc]/[api]/[mod])
- If the diff exposes or changes a user-facing SDK capability, apply first-class product parity (see below) before outputting the description
- If diff touches the
versionofpackages/inference/packages/sdk, or sdk's dep blocks, chain into theqv-sdk-lockstep-syncskill (see "SDK Lockstep Client Sync Trigger" below) - Output complete PR description
- If base is a release branch, chain into the dual-PR flow (see "Release Target Dual-PR Flow" below)
Inference Strategy
Infer first, ask only if uncertain:
Ticket number:
- Extract from branch name pattern:
QVAC-\d+,SDK-\d+ - Extract from commit messages if referenced
- ASK only if no ticket found
Prefix (feat/fix/doc/test/chore/infra):
- Extract from branch name prefix:
feat/,fix/,infra/, etc. - Use majority prefix from commit messages
- If no conventional commits, infer from diff:
- New files/exports →
feat - Bug-related changes →
fix - Only .md files →
doc - Only test files →
test
- New files/exports →
- ASK only if mixed signals or unclear
Tags ([api]/[bc]/[mod]):
[api]: new exported functions/types in public API[bc]: removed/changed existing public API signatures[mod]: changes to model constant definitions- ASK only if change scope is ambiguous
Testing section:
- If test files modified → "Unit tests added/updated for X"
- If no tests → ASK what manual testing was done
Format References
- PR title format: See
docs/gitflow.mdand the validation rules below - PR body template: See
.github/PULL_REQUEST_TEMPLATE/sdk-pod.md
Fill template sections based on the diff analysis. Delete sections that don't apply.
First-class product parity (CLI)
Trigger: the diff touches packages/sdk/server/bare/plugins/**, packages/sdk/client/api/**, a plugin *-config.ts schema, or a request/sampling schema used by serve, and the change is a user-facing inference capability (new modality, new request field, new load-time modelConfig field). Native addon-only diffs skip this.
See packages/sdk/AGENTS.md.
If triggered and packages/cli is unchanged:
- ASK: "CLI not updated. Add CLI in this PR, mark library-only in the body, or skip?"
- Add CLI: stop until the CLI diff is present. Library-only: one-line why in the body. Skip: reminder at the end.
Output Format
ALWAYS output the PR in this copy-ready format, even when making corrections:
## PR Title
```
TICKET prefix[tags]: subject
```
## PR Body
```markdown
## 🎯 What problem does this PR solve?
...
```
gh CLI Integration
After generating the PR description, check for gh CLI:
- Check if
ghis installed:which gh - Check remotes:
git remote -v— identify the org remote (tetherto/qvac) and any fork remote - If available, ask user: "Create PR now with gh CLI?" [Yes / No / Preview first]
- If yes, ensure changes are committed, then push the head branch to the org remote when the user has write access. Only push to a personal fork when org push is unavailable or the user explicitly chooses the fork path
- Create the PR:
# Preferred — org-branch (same-repo) PR.
# ORG_REMOTE = remote whose URL is tetherto/qvac (often `upstream` or `origin`).
git push -u ORG_REMOTE BRANCH
gh pr create \
--repo tetherto/qvac \
--base main \
--head BRANCH \
--title "TICKET prefix: subject" \
--body "..."
# Fallback — personal fork -> org PR (external CI path; needs merge/release fork-ci approval per run):
git push -u FORK_REMOTE BRANCH
gh pr create \
--repo tetherto/qvac \
--base main \
--head FORK_OWNER:BRANCH \
--title "TICKET prefix: subject" \
--body "..."
# Then open in browser:
gh pr view --repo tetherto/qvac BRANCH --web
Important:
--webalone only opens browser for manual creation, does NOT create the PR- For fork PRs, must specify
--repo,--base, and--head FORK_OWNER:BRANCHexplicitly - For org-branch PRs,
--head BRANCH(noowner:) is enough when--repo tetherto/qvac - Do not add fork trust gates on org-branch PRs; baseline CI runs without them. For fork PRs, tell the user a merge/release reviewer must approve the pending
fork-cideployment after reviewing the current head - Commit and push before creating PR
- If gh not available, output the copy-ready markdown format above
- As part of the output, provide a clickable hyperlink (not plain text) to the PR on GitHub.
SDK Lockstep Client Sync Trigger
Trigger: the PR diff (<base>...<head-remote>/<branch> or local HEAD) modifies the version of packages/inference/package.json or packages/sdk/package.json (@qvac/inference is the anchor that drives the pod version), or sdk's dependencies / optionalDependencies / peerDependencies.
When triggered, prompt the user to run qv-sdk-lockstep-sync so the pod stays aligned in the same commit/PR: @qvac/sdk stamped to the inference anchor, and tetherto-qvac-sdk (generated SDK_VERSION / _generated/). Letting them drift creates work for the next release-* cut.
Steps (after Step 8 of Workflow above)
- Detect the trigger condition by inspecting the diff:
git diff <base>...<head-remote>/<branch> -- packages/inference/package.json packages/sdk/package.json(or vs localHEAD) shows changes- Changes touch a
versionline (inference / sdk) OR sdk'sdependencies/optionalDependencies/peerDependenciesblock
- If triggered, ask user: "PR touches sdk's deps/version. Run
qv-sdk-lockstep-syncfor sdk-python?" [Yes / No (skip)] - If yes, read
.agents/skills/qv-sdk-lockstep-sync/SKILL.mdand follow it inline. - Verify:
packages/sdk-pythongenerate.py --checkmust pass. - Stage and commit lockstep client changes onto the same branch BEFORE proceeding to Output step.
Opt-out
To skip lockstep sync for a single run, the user can invoke /qv-sdk-pr-create --no-sync. The skill proceeds normally and emits a reminder at the end: "Reminder: sdk deps/version changed but lockstep clients were not synced. Run /qv-sdk-lockstep-sync before merge."
Docs Artifacts (SDK Releases)
Context: for @qvac/sdk releases, the qv-sdk-changelog skill (Step 8)
now generates the documentation-site API reference + release notes locally and
ships them in this same release PR. There is no longer a separate
auto-generated docs PR (the old docs-release.yml workflow was removed).
Staging works the same as for the rest of the release commit — no special
handling is needed. Step 8's three committable surfaces
(docs/website/content/docs/reference/api/**,
docs/website/content/docs/reference/release-notes/**,
docs/website/src/lib/versions.ts) show up in git status alongside the
changelog, while every generation/build byproduct
(api-data.json, .next/, .source/, out/, dist/, next-env.d.ts,
packages/sdk/dist/) is gitignored and therefore never appears. Review
git status and commit the shown files as usual.
Reviewers should expect the reference/api + reference/release-notes diff in
the release PR alongside the changelog.
Release Target Dual-PR Flow
Trigger: the just-created PR's base is release-<pkg>-<x.y.z> for any SDK pod package.
When triggered, automatically chain into the sdk-backmerge skill so a follow-up PR is also opened against main with the same version-bump + changelog metadata. This applies the gitflow.md "Keep main aligned" rule at PR-creation time so nobody has to remember a follow-up step after the release PR merges.
Preflight before opening the release PR: confirm base matches
^release-<pkg>-\d+\.\d+\.\d+$ and the org head is not release-*
(see Release PR branch naming). Do not open / chain the dual-PR flow against
a short-named cut if publish is expected on merge.
Steps (after Step 5 of gh CLI Integration above)
- Capture context for the backmerge:
- Just-created release PR number and URL
- Release branch name (
release-<pkg>-<x.y.z>) and parsed<pkg>/<x.y.z> - Source head branch, org-remote-qualified when possible (e.g.
ORG_REMOTE/<branch>, or the release PRheadRefOidif the remote tip is missing) - Ticket number from the title
- Invoke the
sdk-backmergeworkflow inline with these inputs (read.agents/skills/qv-sdk-backmerge/SKILL.mdand follow it). - Fail-stop policy — if the backmerge cherry-pick produces a conflict outside
sdk-backmerge's auto-resolve list, STOP. Print:- The release PR URL (success — PR #1 is open)
- The current
git status -sbfrom the conflicted cherry-pick - Resume instructions:
git add <files> && git cherry-pick --continue, then run/qv-sdk-backmerge --resume
- On success, print both PR URLs as clickable hyperlinks, ordered:
- Release PR (target:
release-<pkg>-<x.y.z>) - Backmerge PR (target:
main)
- Release PR (target:
Opt-out
To skip the backmerge for a single run, the user can invoke /qv-sdk-pr-create --no-backmerge. The skill still creates PR #1 normally and prints a reminder pointing to /qv-sdk-backmerge for later.
Quality Checklist
Before outputting the PR description, verify:
- Title follows format:
TICKET prefix[tags]: subject - "What problem" describes user impact, not implementation
- "How it solves" is high-level approach, not line-by-line
- Unused sections are deleted
-
[bc]tag has BEFORE/AFTER code examples -
[api]tag has usage example -
[mod]tag has Added/Removed models list - Description is concise - bullet points, no fluff
- Generated helper notes, template instructions, and tool footers are removed from the PR body
- If the diff is a user-facing SDK capability, CLI was updated in this PR, the body says library-only, or the skip reminder was emitted
- If diff touches the
versionof inference / sdk (or sdk's deps),qv-sdk-lockstep-syncran (or--no-syncwas set with a reminder emitted), and sdk-python checks pass - For sdk releases with generated docs,
git statusshows onlyreference/api/**,reference/release-notes/**, andsrc/lib/versions.tsas committable docs changes — disposable byproducts (api-data.json,out/,.next/,dist/, etc.) are gitignored - If base is
release-<pkg>-<x.y.z>, the dual-PR flow ran (or--no-backmergewas set), and both PR URLs are reported - Release PRs: base is three-part
release-<pkg>-x.y.z; org head ischore/<pkg>-<x.y.z>-changelog(or other non-release-*name) - Head was pushed to the org remote when write access allows; fork path only used as fallback (with
fork-cire-approval called out) - PR is Ready for review when baseline CI is expected (not left as Draft unintentionally)
References
- SDK pod ownership:
.github/teams/sdk.json - Shared SDK and first-class product guidance:
packages/sdk/AGENTS.md - PR template:
.github/PULL_REQUEST_TEMPLATE/sdk-pod.md - Format rules:
docs/gitflow.mdand this skill's validation section - Backmerge skill:
.agents/skills/qv-sdk-backmerge/SKILL.md - sdk lockstep clients:
.agents/skills/qv-sdk-lockstep-sync/SKILL.md - GitFlow:
docs/gitflow.md— still documents fork-first contribution; for internal SDK PRs, prefer the org-branch path in this skill until DevOps updates gitflow - Fork CI trust model:
docs/ci/LABELS.md(fork-ci environment +fork-approval)
Signals
- GitHub stars
- 601
- Forks
- 111
- Last commit
- Sep 2026
Advanced
- Catalog kind
- skill
- Gateway key
qv-sdk-pr-create- Source
- github.com/tetherto/qvac