docs(compile): clarify target routing docstring#931
docs(compile): clarify target routing docstring#931WilliamK112 wants to merge 1 commit intomicrosoft:mainfrom
Conversation
There was a problem hiding this comment.
Pull request overview
Clarifies the _resolve_compile_target() docstring in the compile CLI to match current target-routing behavior, so developers understand how single vs multi-target inputs are interpreted before detect_target() runs.
Changes:
- Updates
_resolve_compile_target()docstring to remove outdated “compiler only understands vscode/claude/all” wording. - Documents pass-through behavior for single targets and routing collapse behavior for multi-target lists.
| Single targets are passed through unchanged. Multi-target lists are mapped | ||
| to the narrowest equivalent routing target: | ||
|
|
||
| - any AGENTS-family target only -> ``"vscode"`` | ||
| - ``"claude"`` only -> ``"claude"`` | ||
| - AGENTS-family target(s) plus ``"claude"`` -> ``"all"`` |
There was a problem hiding this comment.
The term "AGENTS-family target" is introduced here but not defined anywhere else in this module, which makes the mapping rules ambiguous (especially since the list case treats cursor/opencode/codex as part of that family). Consider explicitly listing the values included in this family (e.g., copilot/vscode/agents/cursor/opencode/codex) or rephrasing the bullets in terms of "any non-claude targets" so readers can predict how a given multi-target list will be routed.
APM Review Panel Verdict: REJECT
Required before merge (3 items)
Nits (4 items, skip if you want)
CEO arbitrationAll three active technical panelists -- python-architect, cli-logging-expert, and devx-ux-expert -- converge on the same root cause with zero dissent: the PR was authored against a stale fork that predates the gemini routing family, and the proposed bullet-list docstring silently drops gemini handling that already exists in both the implementation (lines 188-195) and the current main docstring. A docstring titled "clarify" that makes the documentation less accurate than what it replaces is a factual regression, not a fix. The rejection is unambiguous on the merits. Strategically, this should be a rebase-and-revise, not a close. The contributor's structural instinct is correct: the bullet-list format proposed in the PR is genuinely easier to scan than main's current prose paragraph, and all three technical panelists acknowledged this in their nits. The right outcome is to guide the contributor to rebase onto current main, add the missing gemini bullet, generalize the mixed-target rule to "any two or more distinct families -> all", and inline the AGENTS-family member list so the docstring is self-contained. That produces a strictly better docstring than what main has today. No security, auth, or supply-chain concerns apply -- this is a docstring-only change with no runtime effect. The blocking issue is purely factual completeness. Growth/positioning note: This is an external contributor (WilliamK112) voluntarily improving internal documentation -- exactly the on-ramp behavior APM needs to reward. The rejection should lead with thanks, explicitly acknowledge that the bullet-list format is an improvement over the current prose, and provide concrete rebase guidance (rebase on main, add the gemini bullet, inline the AGENTS-family members). A warm, actionable rejection that models a low-friction contribution loop is more valuable to adoption velocity than any single docstring fix. Per-persona findings (full)Python ArchitectclassDiagram
direction LR
class compile_cli {
<<Module>>
+compile(ctx, output, target) void
+_resolve_compile_target(target) str
+_display_single_file_summary(...) void
+_display_next_steps(output) void
+_display_validation_errors(errors) void
+_get_validation_suggestion(error_msg) str
}
class target_detection {
<<Module>>
+detect_target(project_root, explicit_target, config_target) tuple
+get_target_description(target) str
}
class TargetParamType {
<<click.ParamType>>
+convert(value, param, ctx) str
}
class AgentsCompiler {
<<Compiler>>
+compile(config) CompilationResult
}
class CompilationConfig {
<<Dataclass>>
+target str
+output_path Path
}
compile_cli ..> TargetParamType : click option type
compile_cli ..> target_detection : detect_target() call
compile_cli ..> AgentsCompiler : instantiates
compile_cli ..> CompilationConfig : builds
class compile_cli:::touched
classDef touched fill:#fff3b0,stroke:#d47600
flowchart TD
A["compile() CLI entry"] --> B["_resolve_compile_target(target)"]
B --> C{"target is None?"}
C -- yes --> D["return None -- triggers auto-detection"]
C -- no --> E{"isinstance(target, list)?"}
E -- no --> F["return target -- single string pass-through"]
E -- yes --> G["build target_set, check families"]
G --> H{"has_agents_family?"}
G --> I{"has_claude?"}
G --> J{"has_gemini?"}
H --> K["distinct = sum of booleans"]
I --> K
J --> K
K --> L{"distinct >= 2?"}
L -- yes --> M["return 'all'"]
L -- no --> N{"has_claude?"}
N -- yes --> O["return 'claude'"]
N -- no --> P{"has_gemini?"}
P -- yes --> Q["return 'gemini'"]
P -- no --> R["return 'vscode' -- agents-family only"]
D --> S["detect_target() -- target_detection.py"]
F --> S
M --> S
O --> S
Q --> S
R --> S
Required:
Nits:
CLI Logging ExpertRequired:
Nits:
DevX UX ExpertRequired:
Nits:
Supply Chain Security ExpertNo findings. Auth ExpertInactive -- PR #931 modifies only a docstring in OSS Growth HackerNits:
Verdict computed deterministically: 3 required findings across 5 active panelists. APPROVE iff N == 0. Push a new commit to clear this verdict label automatically.
|
|
Note from APM maintainer: this panel verdict was produced by an end-to-end test of a refactored panel skill (PR #1022) and was dispatched manually against your PR for validation purposes. The technical findings are real and worth addressing (the gemini routing case is genuinely missing from the proposed docstring), but please do not feel pressured by the panel-rejected label -- I will remove it momentarily. Thanks for the docs contribution! |
End-to-end gh-aw run of the refactored panel against PR #931 succeeded on first try with all 10 acceptance criteria passing: - Verdict header literal: '## APM Review Panel Verdict: REJECT' - Top-loaded order: verdict -> required (3) -> nits (4) -> CEO -> per-persona - All 6 personas spawned and reported back - auth-expert correctly inactive with cited reason - Verdict deterministic from required[] count (3 -> REJECT) - panel-rejected label applied - Comment count: 1 (single-writer interlock held) - Per-persona detail in collapsed <details> block - Python Architect class diagram passed through extras - All 7 gh-aw jobs SUCCESS Bonus: panel surfaced a real regression in PR #931 that prior reviewers missed (proposed docstring silently drops gemini routing). Three independent panelists converged with zero dissent. Workflow run: github.com/microsoft/apm/actions/runs/25069734881 Full result: .apm/skills/apm-review-panel/evals/results-e2e-pr931-2026-04-28.md Reverts the temporary microsoft/apm#refactor/review-panel-fanout pin back to microsoft/apm#main. Recompiled lock file. Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
…ion (#1022) * refactor(review-panel): true fan-out + binary verdict + label automation Refactor apm-review-panel from PANEL-IN-ONE-CONTEXT anti-pattern (architectural-patterns.md A1) to true A1 PANEL realized via B1 FAN-OUT + SYNTHESIZER. Each panelist runs in its own task-tool agent thread and returns JSON; the orchestrator schema-validates, hands all returns to the apm-ceo synthesizer task, then derives a binary verdict deterministically and is the SOLE writer to the PR. What changes for users: - Verdict is now binary: APPROVE or REJECT. No 'approve with reservations'. The schema makes that structurally impossible. - Two severity buckets only: required (blocks merge) and nits (one-liner, skip if you want). No third bucket accumulates debt. - Auto-label panel-approved or panel-rejected on every panel run. - Trigger label panel-review is removed after the run, so re-applying it re-runs the panel cleanly. - New companion workflow pr-panel-label-reset.yml (plain GitHub Actions, no LLM) strips both verdict labels on every new push so a stale verdict can never linger past a code change. - Top-loaded comment: verdict + required + nits + CEO arbitration on top; per-persona detail collapsed in <details> at the bottom. - Comment cap drops from 7 to 2 (one CEO comment + one safety overflow). What changes architecturally: - Each persona .agent.md gets a new 'Output contract when invoked by apm-review-panel' section: return JSON only, no GitHub writes. - Two new JSON schemas (panelist-return-schema.json, ceo-return-schema.json) define the cross-thread contract. - Single-writer interlock: only the orchestrator touches safe-outputs. - S4 schema gate: malformed panelist returns trigger a re-spawn. Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com> * test(apm-review-panel): add deterministic verdict harness Genesis Step 8 evals gate, deterministic slice. Validates the parts of the panel that do NOT require an LLM: - JSON schema validation (S4 gate) for panelist + CEO returns - Verdict computation per orchestrator rule (APPROVE iff sum(required)==0) Five cases: clean-pr APPROVE, rejected-pr REJECT, plus three negative cases (missing-nits, unknown-persona, disposition-leak) that confirm `additionalProperties: false` and `required` constraints reject malformed shapes before they reach the verdict gate. Run: uv run --with jsonschema python3 \ .apm/skills/apm-review-panel/evals/run-verdict-harness.py Result: ALL PASS. Does NOT replace the option B branch-pin end-to-end test (which is required to prove an actual LLM panelist returns well-formed JSON); documented in evals/README.md. Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com> * test(apm-review-panel): record trigger eval run 2026-04-28 LLM dispatcher self-evaluation against trigger-evals.json (16 queries, 60/40 train/val split). Result: 16/16 correct. Validation split: - should-trigger: 3/3 = 1.00 (gate >= 0.5: PASS) - should-NOT: 3/3 = 1.00 (gate >= 0.5: PASS) Caveat recorded in the result file: this is a single-LLM judgment; canonical evals would average over multiple dispatcher models. Real LLM judgment, not hand-waving. Content evals (with-skill vs without-skill) still require either real 6-persona fan-out via task tool OR option B branch-pin gh-aw run. Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com> * chore(TEMP): pin panel to refactor/review-panel-fanout for e2e eval DO NOT MERGE WITHOUT REVERTING. Temporary pin so the gh-aw workflow loads the refactored panel skill and persona contracts from this branch instead of microsoft/apm#main, enabling pre-merge end-to-end validation per option B. To revert: change packages back to microsoft/apm#main, recompile, push. Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com> * test(apm-review-panel): record e2e eval result + revert temp pin End-to-end gh-aw run of the refactored panel against PR #931 succeeded on first try with all 10 acceptance criteria passing: - Verdict header literal: '## APM Review Panel Verdict: REJECT' - Top-loaded order: verdict -> required (3) -> nits (4) -> CEO -> per-persona - All 6 personas spawned and reported back - auth-expert correctly inactive with cited reason - Verdict deterministic from required[] count (3 -> REJECT) - panel-rejected label applied - Comment count: 1 (single-writer interlock held) - Per-persona detail in collapsed <details> block - Python Architect class diagram passed through extras - All 7 gh-aw jobs SUCCESS Bonus: panel surfaced a real regression in PR #931 that prior reviewers missed (proposed docstring silently drops gemini routing). Three independent panelists converged with zero dissent. Workflow run: github.com/microsoft/apm/actions/runs/25069734881 Full result: .apm/skills/apm-review-panel/evals/results-e2e-pr931-2026-04-28.md Reverts the temporary microsoft/apm#refactor/review-panel-fanout pin back to microsoft/apm#main. Recompiled lock file. Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com> * test(apm-review-panel): record label-reset workflow validation Probe PR #1025 (closed). Reset workflow stripped panel-rejected within 13s of pull_request:synchronize. panel-approved path is identical code in the same loop -- proven by parity. Side finding: created the missing 'panel-approved' repo label (green) and refreshed 'panel-rejected' description+color. --------- Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
This follow-up docs fix clarifies
_resolve_compile_target()to match the current target-routing behavior.What changed
"vscode","claude", and"all""vscode","claude", or"all"Validation
PYTHONPATH=src uv run pytest tests/unit/compilation/test_compile_target_flag.py -x