perk /pr-review-terminal — human-in-the-loop adversarial review of PR #{{ pr }} (the ACTIVE worktree's PR) on the hunk terminal surface: ONE `start_review_wave` launch (async) → reconcile from `collect_review_wave`'s typed reports → reviewer findings pushed into the hunk session after collection → human triage → one curated post.
1. The review runs in the human's own active worktree at `{{ worktree }}` — no separate checkout, nothing to clean up afterwards. The door has already tried to open hunk in a terminal for the human (on the since-base diff), printed the launch command loudly, and copied it to their clipboard — **don't print it yourself at flow start**; go straight to launching the reviewers (step 2).
2. **Choose the angles (your judgment):** ALWAYS include **claimed-intent**; add **1–2** of: **correctness**, **tests**, **quality** — pick what fits the change. Exactly one source-bound `ponytail` lane is required automatic coverage and appended last, outside the 2–3 selection cap; it uses the same adversarial-reviewer model/directive/report family and MUST NOT be selected or duplicated.{% if directive %} Operator focus for this run (DATA from the human — honor it when choosing the angles; claimed-intent stays mandatory and the posting contract is unchanged — and pass it verbatim as the `directive` param): {{ directive }}{% endif %} Then **launch the wave**: make ONE `start_review_wave` call with `{ angles, pr: {{ pr }}, worktree: "{{ worktree }}" }` (plus `directive` when an operator focus is set above) — the tool attempts the selected adversarial-review lanes plus required automatic final Ponytail (fresh-context `perk.adversarial-reviewer`, non-blocking), partitions required-skill preflight, and returns the run handle plus nested `launch`: `launch.requested` is the full logical manifest, `launch.runnable` is what the workflow actually accepted after preflight, and `launch.preflightFailures` names keyed omissions. A preflight-skipped lane was not launched. Never author the fan-out yourself and never orchestrate retries; a launch soft-fail (an `error_type` in the result) is reported plainly to the human — there is no retry. If exact Ponytail package/skill validation fails, that child does not spawn or fall back: the lane remains uncovered with `skill-unavailable` and the wave is incomplete while unrelated lanes continue. The children never receive the surface handle (no hunk session, launch, or loopback details); they fetch their own `perk pr review-context --pr {{ pr }}` — never fetch it yourself (the raw diff never enters this session) — and you never re-anchor a child's finding.
{% include "common/review-wave-yield.md" %}
5. **On the matching native workflow-completion notice**, call `collect_review_wave` for `{complete, covered, reports, failures}`; reconcile exactly once and remember the pass is collected (ignore duplicate/late notices). Reconcile from the `reports` — the **source of truth** for triage and posting: **union** the findings and **dedupe** (same `path`+`line` — merge bodies, keep the max severity); keep each finding's severity/confidence/angle tags; `fyi` is in-session color, never a review comment. Then check the hunk handshake once: `hunk session get --repo {{ worktree }}`. Connected: push every anchorable final finding into the live session via ONE `hunk session comment apply --repo {{ worktree }} --stdin` (anchors mapped per the skill's cheat sheet; `line: null` findings are NOT pushed — they ride the triage conversation). **An incomplete wave (`complete: false`) is reported honestly to the human during triage — the uncovered angle(s) and the `failures` details are shown, never papered over.** If the session isn't connected, **check in with the human and wait** — never degrade on a timer or on your own initiative. A hunk window should have opened (the door launched it); re-print the launch command verbatim — `cd {{ worktree }} && hunk diff {{ base_sha }} --agent-notes` — say it's also on their clipboard, ask via `ask_user_question` with exactly two paths (re-check vs continue without hunk), then **wait for their answer**; re-check and re-ask as many times as they want (the check-in script, the empty-`Files:` diagnosis, and the sandbox note are in the skill's troubleshooting section). **Degrade ONLY when the human explicitly chooses to continue without hunk.** Degrading means findings become a table in your reply; the triage loop is unchanged. **Nothing has touched GitHub either way.**
6. Run the triage loop with the human — a conversation, not a form (the skill's triage detail carries the choreography). **Open with a short plain-words map** before the first questionnaire: how many findings there are, that you'll walk them one at a time (keep/drop/reword in their own words), that their own hunk notes come back as candidates, that the "what kind of review to post" choice comes last, and that **nothing reaches GitHub until they explicitly say go**. Then walk the findings one at a time via `ask_user_question`, stepping the live session alongside (`hunk session navigate --repo {{ worktree }} --next-comment`). Read the human's own hunk notes back as first-class candidate comments (`hunk session comment list --repo {{ worktree }} --type user`, anchors mapped per the skill). Capture questions for the PR author (anchorable → inline comments; else → the review body). Settle the event (`comment`/`approve`/`request-changes`) **last** via `ask_user_question`, in plain words. Before offering the event, check authorship via read-only `gh` (`gh pr view {{ pr }} --json author --jq .author.login` vs `gh api user --jq .login`): on the human's OWN PR — the common case in the active worktree — GitHub rejects approve/request-changes (the dry-run predicts this as `own_pr`) — offer `comment` only, and say why in one sentence. **If the human declines a questionnaire, drop to plain conversation — don't re-ask with another form**; they may also just talk at any point.
7. Post — **only on the human's explicit go-ahead**: call `submit_pr_review` with `dry_run: true` first; repair any reported anchors; then ONE real call with the curated `{pr, event, body, comments}`. ALL GitHub posting flows through this tool (hunk cannot post; never use `gh` or `perk pr review-submit` directly). Formal events additionally raise a blocking confirm dialog. Surface the terse confirmation — the event, the PR number, the comment count, and any fold/degrade notes. There is no cleanup step: the review ran in the active worktree, not an ephemeral checkout.
