@ferris1225/pi-subagents 2.2.0 → 2.3.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -239,6 +239,15 @@ currently unavailable vision selection is skipped immediately without rewriting
239
239
  it. A vision-flagged auto-fix chain keeps the flag for worker/re-review rounds
240
240
  because they may need to inspect the same images.
241
241
 
242
+ As a deterministic fallback, a brief that names an image file (an extension such
243
+ as `.png`, `.jpg`, `.webp`) or describes frontend/UI work — Vue/React/Svelte
244
+ pages, mockups, screenshots, page styling — is dispatched as
245
+ vision even without the flag: the model cannot be swapped mid-run, so a worker
246
+ that screenshots and visually verifies what it builds must start on a
247
+ vision-capable model. How do you verify which model ran? The live widget line,
248
+ dispatch result row, and `subagent_status` all show each run's effective model
249
+ id, and a selected→main handoff is labeled with its origin.
250
+
242
251
  ### Controlling and stopping
243
252
 
244
253
  Dispatch confirmations, tool result rows, and completion blocks all show the
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@ferris1225/pi-subagents",
3
- "version": "2.2.0",
3
+ "version": "2.3.1",
4
4
  "description": "Controllable background sub-agent threads for pi: specialized roles, capability-aware thinking, direct main-model fallback, auto-fix chains, and Git worktree isolation.",
5
5
  "type": "module",
6
6
  "license": "MIT",
package/src/dispatch.ts CHANGED
@@ -59,7 +59,7 @@ export { FORK_CONTINUATION_PROMPT, isWorktreeCapableAgent } from "./thread-lifec
59
59
  const NON_BLANK_TASK_OPTIONS = { minLength: 1, pattern: "\\S" } as const;
60
60
 
61
61
  const VISION_DESCRIPTION =
62
- "Set true when the task may require viewing images (screenshots, mockups, designs) — the configured vision model is used first, then model-level failures hand directly to the current main-window model";
62
+ "Set true when the task may require viewing images (screenshots, mockups, designs) — the configured vision model is used first, then model-level failures hand directly to the current main-window model. A task that names an image file or describes frontend/UI work (Vue/React, mockups, screenshots, page styling) is dispatched as vision automatically";
63
63
 
64
64
  const ISOLATION_DESCRIPTION =
65
65
  "Filesystem isolation: shared uses the caller's working tree; worktree creates a detached temporary Git worktree (write-capable agents, including worker and cleaner, only)";
@@ -95,6 +95,27 @@ export function defaultIsolationMode(mode: "single" | "parallel", agentName: str
95
95
  return mode === "parallel" && agentName === "worker" ? "worktree" : "shared";
96
96
  }
97
97
 
98
+ const IMAGE_FILE_PATTERN = /\.(?:png|jpe?g|webp|gif|bmp|tiff?|avif)\b/i;
99
+ /** Frontend/UI work: the agent may screenshot and visually verify what it
100
+ * builds, and the model cannot be swapped mid-run — vision must be on at
101
+ * spawn. Only language-neutral signals: code terms and file names stay in
102
+ * English even in non-English briefs; purely semantic wording is the LLM's
103
+ * job via the vision flag, not a per-language keyword list. Word boundaries
104
+ * keep ordinary words (build, guide, reactor) from matching. */
105
+ const FRONTEND_PATTERN = /\b(?:vue|react|svelte|angular|nuxt|next\.?js|vite|tailwind|screenshots?|mockups?|wireframes?|UI)\b/i;
106
+ const FRONTEND_FILE_PATTERN = /\.(?:vue|html?|css|svg)\b/i;
107
+
108
+ /** Deterministic vision fallback: a brief that names an image file or describes
109
+ * frontend/UI work is vision work even when the dispatcher forgot the flag —
110
+ * prompting alone cannot guarantee `vision: true`, and a non-vision model can
111
+ * neither see reference images nor visually verify what it builds. */
112
+ export function taskImpliesVision(task: string): boolean {
113
+ return IMAGE_FILE_PATTERN.test(task) || FRONTEND_FILE_PATTERN.test(task) || FRONTEND_PATTERN.test(task);
114
+ }
115
+
116
+ const wantsVision = (flag: boolean | undefined, task: string): boolean =>
117
+ flag === true || taskImpliesVision(task);
118
+
98
119
  const autoFixRootTails = new Map<string, Promise<void>>();
99
120
 
100
121
  async function canonicalAutoFixRoot(cwd: string): Promise<string> {
@@ -628,7 +649,7 @@ export function registerSubagentTool(pi: ExtensionAPI, runtime: SubagentRuntime)
628
649
  item.agent,
629
650
  item.task,
630
651
  item.cwd,
631
- item.vision === true,
652
+ wantsVision(item.vision, item.task),
632
653
  defaultIsolationMode("parallel", item.agent, item.isolation as IsolationMode | undefined),
633
654
  ));
634
655
  }
@@ -666,7 +687,7 @@ export function registerSubagentTool(pi: ExtensionAPI, runtime: SubagentRuntime)
666
687
  params.agent as string,
667
688
  params.task as string,
668
689
  params.cwd,
669
- params.vision === true,
690
+ wantsVision(params.vision, params.task as string),
670
691
  defaultIsolationMode("single", params.agent as string, params.isolation as IsolationMode | undefined),
671
692
  );
672
693
  if (result.exitCode !== -1) {
package/src/prompt.ts CHANGED
@@ -67,7 +67,7 @@ ${hasMultiple ? `- Run INDEPENDENT tasks in parallel: one subagent call with a \
67
67
  - Trust but verify: a sub-agent's summary describes intent, not outcome. Check the actual changes/results before reporting work done.
68
68
  ${hasExplore ? "- Treat `explore` findings as a retrieval index, never as sole proof for edits, deletion, security, compatibility, persistence, or dynamic reachability. Re-read load-bearing files before acting. An underpowered model can be false economy on complex dynamic, concurrent, migration, or security-sensitive code; use a stronger model or specialist there.\n" : ""}
69
69
  Vision tasks:
70
- - Judge whether a delegated task may require viewing images (frontend screenshots, mockups, design files, visual regression comparisons). If it might, pass \`vision: true\` in the subagent call and give the sub-agent the exact image paths — it reads them with its read tool.
70
+ - Judge whether a delegated task may require viewing images (frontend screenshots, mockups, design files, visual regression comparisons). If it might, pass \`vision: true\` in the subagent call and give the sub-agent the exact image paths — it reads them with its read tool. Naming an image file or describing frontend/UI work (Vue/React page, mockup, page styling) dispatches as vision automatically, but keep passing the flag for image work described without those signals.
71
71
  - \`vision: true\` runs the sub-agent on the vision-capable model configured in /subagents-setup; when none is configured it falls back to the main session's current model. Do not skip the flag because the agent's default model looks fast — a non-vision model cannot see the images.
72
72
 
73
73
  Result handoff (do not re-state):