agent-router
전문 에이전트 자동 라우팅. 법률, 재무, 특허, SEO, 마케팅, 기획, BM 설계(BMC/Lean/JTBD/Wardley/Blue Ocean/Lightning Sprint), 코드리뷰, 아키텍처, 견적, CRM, HR/인사, 노무(노동법/해고/산재/취업규칙), 리서치, 데이터…
8 reviewer 병렬 검증 (Workflow tool 결정론 fan-out + CRITICAL/HIGH adversarial 재검증)
> /plugin marketplace add sangrokjung/claude-forge > /plugin install claude-forge@claude-forge
How it fires
How this command gets triggered: by you, by Claude, or both.
/handoff-verifyContext preview
What this command does when you run it.
8 reviewer 병렬 검증 (Workflow tool 결정론 fan-out + CRITICAL/HIGH adversarial 재검증)
allowed-tools: Bash(git:*), Bash(command:*), Bash(python3:*), Read, Workflow, Skill(sync-docs), Skill(commit-push-pr) description: 8 reviewer 병렬 검증 (Workflow tool 결정론 fan-out + CRITICAL/HIGH adversarial 재검증) argument-hint: "[의도 텍스트]"
> 트리거 주체 (§12, 2026-06-12): 본 스킬은 이미 Skill이다 — §12 "스킬화"는 완료 상태다. 미해결이었던 것은 **트리거 주체**다. 비단순 코드 변경 완료 후 **에이전트가 자율 호출**한다(사람이 매번 `/handoff-verify`를 입력하는 것은 폴백). 근거: verification.md "자율 검증 §11".
**Workflow tool 기반** pre-merge 검증 게이트. v7의 "단일 메시지 8× `Task()` 수동 fan-out"을 Workflow tool `parallel()`로 전환 — 결정론적 동시 spawn(사일런트 spawn 실패 0) + `schema` 강제 구조화 회수 + CRITICAL/HIGH **적대적 재검증**(false positive 제거).
| Reviewer | 영역 | gating | |----------|------|--------| | code-reviewer | 정적 보안+품질 | always | | verify-agent | typecheck/lint/build/test 실행 (수정 금지) | always | | security-reviewer | OWASP+STRIDE | always | | database-reviewer | RLS/EXPLAIN/N+1 | always | | a11y-reviewer | WCAG 2.1 AA | always | | performance-reviewer | Core Web Vitals | always | | codex-reviewer | GPT-5.5 크로스모델 | `command -v codex` | | gemini-reviewer | Gemini 프론트엔드 | `command -v gemini` |
워크플로우 SSOT: `~/.claude/skills/handoff-verify/handoff-verify.workflow.js` reviewer 상세 체크리스트: `~/.claude/skills/handoff-verify/reviewer-prompts.md`
| v7 (Task 수동 fan-out) | v8 (Workflow tool) | |---|---| | 단일 응답에서 8× `Task()` 발화 — 비결정적, 사일런트 spawn 실패 가능 | `parallel(8)` 결정론 fan-out — 모든 reviewer 회수 보장 | | §3 "발화 검증 가드"(C3)로 7/8 누락 재시도 | 구조적 불필요 — barrier가 8/8 보장 | | perl placeholder 치환 → 메인이 추출 → Task() | `args` 객체 1회 주입 | | 결과 Severity 분류·dedup LLM 추론 | `schema` 강제 + 스크립트 결정론 집계·dedup | | dedup 없음 (D5) | file_line+severity 키 dedup (reviewer 목록 보존) | | 없음 | **CRITICAL/HIGH adversarial 재검증** — 오탐 제거 |
# 변경 없으면 abort
if [ -z "$(git status --short)" ]; then
echo "변경사항 없음. git status 빈 결과. /handoff-verify 종료."
exit 0
fi
# CLI 가용성 안내 (미설치 reviewer는 워크플로우가 자동 skip)
CODEX_OK=$(command -v codex >/dev/null 2>&1 && echo true || echo false)
GEMINI_OK=$(command -v gemini >/dev/null 2>&1 && echo true || echo false)
if [ "$CODEX_OK" = "false" ] || [ "$GEMINI_OK" = "false" ]; then
echo "⚠️ 크로스모델 가용성 — codex:$CODEX_OK gemini:$GEMINI_OK"
echo " 미설치 reviewer는 자동 skip + 푸터 명시. 설치: Read ~/.claude/skills/handoff-verify/cli-setup.md"
fi
# args JSON 생성 (python3로 안전 인코딩 — diff 8KB·따옴표·줄바꿈 이스케이프)
python3 - "$ARGUMENTS" << 'PYEOF'
import json, os, subprocess, sys
def sh(cmd):
try:
return subprocess.run(cmd, shell=True, capture_output=True, text=True).stdout
except Exception:
return ""
def has(cmd):
return subprocess.run(f"command -v {cmd}", shell=True,
capture_output=True).returncode == 0
def read(path, fallback="(없음)"):
try:
with open(path) as f:
return f.read().strip() or fallback
except Exception:
return fallback
intent = sys.argv[1] if len(sys.argv) > 1 and sys.argv[1].strip() else "(없음)"
dod = sh("grep -E '^- \\[ \\] DoD-' .claude/sprint-contract.md 2>/dev/null").strip() or "(없음)"
payload = {
"intent": intent,
"changed_files": sh("git diff --name-only HEAD").strip() or "(없음)",
"diff": sh("git diff HEAD")[:8000] or "(없음)",
"handoff": read(".claude/handoff.md"),
"dod": dod,
"has_codex": has("codex"),
"has_gemini": has("gemini"),
}
print(json.dumps(payload, ensure_ascii=False))
PYEOF
# 워크플로우 본체 경로 탐지 (.claude 우선 → dotclaude fallback. 멀티PC 견고 — 동기화 가정 제거)
WF_PATH=$(ls ~/.claude/skills/handoff-verify/handoff-verify.workflow.js 2>/dev/null \
|| ls ~/qjc-office/dotclaude/skills/handoff-verify/handoff-verify.workflow.js 2>/dev/null)
if [ -z "$WF_PATH" ] || [ ! -f "$WF_PATH" ]; then
echo "❌ handoff-verify.workflow.js 미발견 — 동기화 필요 (/dc pull 또는 /company-sync)"; exit 1
fi
echo "WF_PATH=$WF_PATH"위 bash 출력의 **마지막 JSON 줄**(payload)과 **`WF_PATH=` 줄**을 2단계에 사용한다.
메인 세션은 `Workflow` tool을 **scriptPath + args**로 1회 호출:
Workflow({
scriptPath: "<1단계 출력의 WF_PATH 값 (절대경로 — 하드코딩 금지)>",
args: <1단계 payload JSON을 JSON.parse 한 실제 객체>
})워크플로우 반환 형식:
{
"verdict": "PASS | WARN | FAIL",
"summary": { "critical": N, "high": N, "medium": N, "low": N, "refuted": N },
"confirmed_findings": [ { "severity", "file_line", "issue", "reviewers": [...] } ],
"refuted_findings": [ { ..., "refute_reason" } ], // adversarial로 제거된 오탐
"reviews": [ { "reviewer", "applicable", "verdict", "evidence", "findings", "counts": { "critical": N, "high": N, "medium": N, "low": N } } ],
"na_reviewers": [...], "error_reviewers": [...], "skipped_reviewers": [...]
}══════════════════════════════════════════════════════════════════ /handoff-verify — Workflow Fan-out (8 reviewers + adversarial) ══════════════════════════════════════════════════════════════════ 🔴 CRITICAL (N): • <reviewers>: <file:line> — <issue> 🟠 HIGH (N): ... 🟡 MEDIUM (N): ... 🟢 LOW (N): ... 🧪 Refuted (N): <file:line> — <refute_reason> (adversarial 검증으로 제거된 오탐) ℹ️ N/A: <na_reviewers> (영역 변경 없음) ⚠️ FAILED: <error_reviewers> / Skipped: <skipped_reviewers (CLI 미설치)> ───────────────────────────────────────────────────────────────── 요약: 🔴N / 🟠N / 🟡N / 🟢N (refuted N) | Verdict: PASS / WARN / FAIL ══════════════════════════════════════════════════════════════════
Verdict 룰 (워크플로
oh-my-zsh for Claude Code — 16 agents, 35 commands, 32 skills, 21 safety hooks in one install. v4.0 adds an adversarial review loop: a second agent that never sees the first one's reasoning. MIT.
Repo: sangrokjung/claude-forge
전문 에이전트 자동 라우팅. 법률, 재무, 특허, SEO, 마케팅, 기획, BM 설계(BMC/Lean/JTBD/Wardley/Blue Ocean/Lightning Sprint), 코드리뷰, 아키텍처, 견적, CRM, HR/인사, 노무(노동법/해고/산재/취업규칙), 리서치, 데이터…
머지 전 /sync-docs 문서 동기화 의무 게이트 → 검증 → 커밋 & PR & 머지 + MCP 알림 (v7)