@opencow-ai/opencow-agent-sdk 0.4.22 → 0.4.24

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.
Files changed (44) hide show
  1. package/dist/capabilities/SdkTool.d.ts +5 -0
  2. package/dist/capabilities/lsp/LSPServerManager.d.ts +2 -1
  3. package/dist/capabilities/mcp/types.d.ts +3 -3
  4. package/dist/capabilities/plugins/loadPluginAgents.d.ts +6 -0
  5. package/dist/capabilities/plugins/loadPluginCommands.d.ts +10 -0
  6. package/dist/capabilities/plugins/loadPluginHooks.d.ts +5 -0
  7. package/dist/capabilities/plugins/loadPluginOutputStyles.d.ts +6 -0
  8. package/dist/capabilities/plugins/lspPluginIntegration.d.ts +1 -0
  9. package/dist/capabilities/plugins/mcpPluginIntegration.d.ts +1 -0
  10. package/dist/capabilities/plugins/pluginOptionsStorage.d.ts +1 -0
  11. package/dist/capabilities/plugins/schemas.d.ts +4 -4
  12. package/dist/capabilities/plugins/sdkPluginRuntime.d.ts +35 -0
  13. package/dist/capabilities/todo/types.d.ts +2 -2
  14. package/dist/capabilities/tools/AgentTool/AgentTool.d.ts +9 -8
  15. package/dist/capabilities/tools/AgentTool/agentMerge.d.ts +1 -0
  16. package/dist/capabilities/tools/AgentTool/inputSchema.d.ts +3 -3
  17. package/dist/capabilities/tools/AgentTool/loadAgentsDir.d.ts +1 -0
  18. package/dist/capabilities/tools/AgentTool/runAgent.d.ts +3 -3
  19. package/dist/capabilities/tools/TodoWriteTool/TodoWriteTool.d.ts +10 -10
  20. package/dist/cli.mjs +707 -359
  21. package/dist/client.d.ts +2 -0
  22. package/dist/client.js +6156 -846
  23. package/dist/controller/dispatch/permissionPreDecision.d.ts +22 -0
  24. package/dist/entrypoints/sdk/controlSchemas.d.ts +139 -139
  25. package/dist/entrypoints/sdk/coreSchemas.d.ts +57 -57
  26. package/dist/entrypoints/sdk/runtimeTypes.d.ts +93 -1
  27. package/dist/lib/toolInputNullCoercion.d.ts +1 -1
  28. package/dist/permissions/PermissionMode.d.ts +2 -2
  29. package/dist/permissions/PermissionPromptToolResultSchema.d.ts +1 -1
  30. package/dist/permissions/PermissionUpdateSchema.d.ts +1 -1
  31. package/dist/providers/anthropic/teleport/api.d.ts +3 -3
  32. package/dist/sdk.js +6156 -846
  33. package/dist/session/forkedAgent.d.ts +2 -1
  34. package/dist/session/layout/schemas.d.ts +12 -12
  35. package/dist/session/settings/types.d.ts +3 -3
  36. package/dist/session/state/index.d.ts +1 -1
  37. package/dist/session/state/registries.d.ts +4 -0
  38. package/dist/session/state/types.d.ts +4 -0
  39. package/dist/session/tasks.d.ts +2 -2
  40. package/dist/session/teammateMailbox.d.ts +2 -2
  41. package/dist/types/command.d.ts +2 -0
  42. package/dist/types/plugin.d.ts +2 -0
  43. package/dist/types/toolRuntime.d.ts +18 -0
  44. package/package.json +1 -1
package/dist/cli.mjs CHANGED
@@ -33074,7 +33074,10 @@ var init_schemas3 = __esm(() => {
33074
33074
  NO_AUTO_UPDATE_OFFICIAL_MARKETPLACES = new Set(["knowledge-work-plugins"]);
33075
33075
  BLOCKED_OFFICIAL_NAME_PATTERN = /(?:official[^a-z0-9]*(anthropic|claude)|(?:anthropic|claude)[^a-z0-9]*official|^(?:anthropic|claude)[^a-z0-9]*(marketplace|plugins|official))/i;
33076
33076
  NON_ASCII_PATTERN = /[^\u0020-\u007E]/;
33077
- RelativePath = lazySchema(() => exports_external.string().startsWith("../../utils/plugins"));
33077
+ RelativePath = lazySchema(() => exports_external.string().min(1).refine((path9) => {
33078
+ const normalized = path9.replaceAll("\\", "/");
33079
+ return !normalized.includes("\x00") && !normalized.startsWith("/") && !/^[a-z][a-z0-9+.-]*:/i.test(normalized) && normalized.split("/").every((segment) => segment !== "..");
33080
+ }, "Path must be relative and remain within the plugin root"));
33078
33081
  RelativeJSONPath = lazySchema(() => RelativePath().endsWith(".json"));
33079
33082
  McpbPath = lazySchema(() => exports_external.union([
33080
33083
  RelativePath().refine((path9) => path9.endsWith(".mcpb") || path9.endsWith(".dxt"), {
@@ -88740,7 +88743,11 @@ function buildQueryContextFromSdk(options) {
88740
88743
  agentColorIndex: 0,
88741
88744
  systemPromptSectionCache: new Map,
88742
88745
  cachedClaudeMdContent: null,
88743
- settingsCache: { session: null, perSource: new Map, parseFile: new Map },
88746
+ settingsCache: {
88747
+ session: null,
88748
+ perSource: new Map,
88749
+ parseFile: new Map
88750
+ },
88744
88751
  memoryExtractionState: {
88745
88752
  config: {
88746
88753
  minimumMessageTokensToInit: 1e4,
@@ -88761,7 +88768,9 @@ function buildQueryContextFromSdk(options) {
88761
88768
  conditional: new Map,
88762
88769
  activatedConditional: new Set,
88763
88770
  loaded: createSignal()
88764
- }
88771
+ },
88772
+ pluginDataPaths: new Map,
88773
+ lspManager: null
88765
88774
  },
88766
88775
  diagnostics: createFreshDiagnostics(),
88767
88776
  provider: options.provider ?? resolveProviderFromEnv(freezeEnvMap(options.env)),
@@ -89425,6 +89434,25 @@ function resetSdkInitState() {
89425
89434
  r.initJsonSchema = null;
89426
89435
  r.registeredHooks = null;
89427
89436
  }
89437
+ function setExplicitPluginRuntimeContext(dataPaths, lspManager) {
89438
+ const registries2 = getQueryContext().registries;
89439
+ registries2.pluginDataPaths = new Map(dataPaths);
89440
+ registries2.lspManager = lspManager;
89441
+ }
89442
+ function tryGetExplicitPluginDataPath(pluginId) {
89443
+ try {
89444
+ return getQueryContext().registries.pluginDataPaths.get(pluginId);
89445
+ } catch {
89446
+ return;
89447
+ }
89448
+ }
89449
+ function tryGetSessionLspManager() {
89450
+ try {
89451
+ return getQueryContext().registries.lspManager ?? undefined;
89452
+ } catch {
89453
+ return;
89454
+ }
89455
+ }
89428
89456
  function addInvokedSkill(skillName, skillPath, content, agentId = null) {
89429
89457
  const key = `${agentId ?? ""}:${skillName}`;
89430
89458
  getQueryContext().registries.invokedSkills.set(key, {
@@ -89876,6 +89904,7 @@ __export(exports_state, {
89876
89904
  setCwdState: () => setCwdState,
89877
89905
  setDirectConnectServerUrl: () => setDirectConnectServerUrl,
89878
89906
  setEnvVar: () => setEnvVar,
89907
+ setExplicitPluginRuntimeContext: () => setExplicitPluginRuntimeContext,
89879
89908
  setFastModeHeaderLatched: () => setFastModeHeaderLatched,
89880
89909
  setFlagSettingsInline: () => setFlagSettingsInline,
89881
89910
  setHasDevChannels: () => setHasDevChannels,
@@ -89910,7 +89939,9 @@ __export(exports_state, {
89910
89939
  setThinkingClearLatched: () => setThinkingClearLatched,
89911
89940
  snapshotOutputTokensForTurn: () => snapshotOutputTokensForTurn,
89912
89941
  switchSession: () => switchSession,
89942
+ tryGetExplicitPluginDataPath: () => tryGetExplicitPluginDataPath,
89913
89943
  tryGetQueryContext: () => tryGetQueryContext,
89944
+ tryGetSessionLspManager: () => tryGetSessionLspManager,
89914
89945
  unregisterCreatedTeam: () => unregisterCreatedTeam
89915
89946
  });
89916
89947
  var init_state = __esm(() => {
@@ -92241,9 +92272,7 @@ function createBootQueryContext() {
92241
92272
  resolvedCwd = "";
92242
92273
  }
92243
92274
  const sessionId = randomUUID3();
92244
- const {
92245
- computeSessionPaths: computeSessionPaths2
92246
- } = (init_paths(), __toCommonJS(exports_paths));
92275
+ const { computeSessionPaths: computeSessionPaths2 } = (init_paths(), __toCommonJS(exports_paths));
92247
92276
  const { resolveLayoutProfile: resolveLayoutProfile2, DEFAULT_LAYOUT_PROFILE: DEFAULT_LAYOUT_PROFILE2 } = (init_LayoutProfile(), __toCommonJS(exports_LayoutProfile));
92248
92277
  const { getManagedFilePath: getManagedFilePath2 } = (init_managedPath(), __toCommonJS(exports_managedPath));
92249
92278
  const { homedir: homedir11 } = __require("node:os");
@@ -92323,7 +92352,11 @@ function createBootQueryContext() {
92323
92352
  agentColorIndex: 0,
92324
92353
  systemPromptSectionCache: new Map,
92325
92354
  cachedClaudeMdContent: null,
92326
- settingsCache: { session: null, perSource: new Map, parseFile: new Map },
92355
+ settingsCache: {
92356
+ session: null,
92357
+ perSource: new Map,
92358
+ parseFile: new Map
92359
+ },
92327
92360
  memoryExtractionState: {
92328
92361
  config: {
92329
92362
  minimumMessageTokensToInit: 1e4,
@@ -92344,7 +92377,9 @@ function createBootQueryContext() {
92344
92377
  conditional: new Map,
92345
92378
  activatedConditional: new Set,
92346
92379
  loaded: createSignal()
92347
- }
92380
+ },
92381
+ pluginDataPaths: new Map,
92382
+ lspManager: null
92348
92383
  },
92349
92384
  diagnostics: createFreshDiagnostics(),
92350
92385
  provider: (() => {
@@ -92414,7 +92449,11 @@ function deriveSubagentRegistries(parent) {
92414
92449
  agentColorIndex: parent.agentColorIndex,
92415
92450
  systemPromptSectionCache: new Map,
92416
92451
  cachedClaudeMdContent: null,
92417
- settingsCache: { session: null, perSource: new Map, parseFile: new Map },
92452
+ settingsCache: {
92453
+ session: null,
92454
+ perSource: new Map,
92455
+ parseFile: new Map
92456
+ },
92418
92457
  memoryExtractionState: {
92419
92458
  config: {
92420
92459
  minimumMessageTokensToInit: 1e4,
@@ -92429,7 +92468,9 @@ function deriveSubagentRegistries(parent) {
92429
92468
  systemPromptInjection: null,
92430
92469
  sentSkillNames: new Set,
92431
92470
  skillListingSuppressNext: false,
92432
- dynamicSkills: parent.dynamicSkills
92471
+ dynamicSkills: parent.dynamicSkills,
92472
+ pluginDataPaths: parent.pluginDataPaths,
92473
+ lspManager: parent.lspManager
92433
92474
  };
92434
92475
  }
92435
92476
  function cloneHookRegistry(registry2) {
@@ -94777,7 +94818,7 @@ function printStartupScreen() {
94777
94818
  const sLen = ` ● ${sL} Ready — type /help to begin`.length;
94778
94819
  out.push(boxRow(sRow, W2, sLen));
94779
94820
  out.push(`${rgb(...BORDER)}╚${"═".repeat(W2 - 2)}╝${RESET}`);
94780
- out.push(` ${DIM}${rgb(...DIMCOL)}opencow ${RESET}${rgb(...ACCENT)}v${"0.4.22"}${RESET}`);
94821
+ out.push(` ${DIM}${rgb(...DIMCOL)}opencow ${RESET}${rgb(...ACCENT)}v${"0.4.24"}${RESET}`);
94781
94822
  out.push("");
94782
94823
  process.stdout.write(out.join(`
94783
94824
  `) + `
@@ -144752,7 +144793,7 @@ function pluginDataDirPath(pluginId) {
144752
144793
  return join46(getPluginsDirectory(), "data", sanitizePluginId(pluginId));
144753
144794
  }
144754
144795
  function getPluginDataDir(pluginId) {
144755
- const dir = pluginDataDirPath(pluginId);
144796
+ const dir = tryGetExplicitPluginDataPath(pluginId) ?? pluginDataDirPath(pluginId);
144756
144797
  getFsImplementation().mkdirSync(dir, { recursive: true });
144757
144798
  return dir;
144758
144799
  }
@@ -144760,7 +144801,9 @@ async function getPluginDataDirSize(pluginId) {
144760
144801
  const dir = pluginDataDirPath(pluginId);
144761
144802
  let bytes = 0;
144762
144803
  const walk = async (p) => {
144763
- for (const entry of await getFsImplementation().readdir(p, { withFileTypes: true })) {
144804
+ for (const entry of await getFsImplementation().readdir(p, {
144805
+ withFileTypes: true
144806
+ })) {
144764
144807
  const full = join46(p, entry.name);
144765
144808
  if (entry.isDirectory()) {
144766
144809
  await walk(full);
@@ -144921,7 +144964,7 @@ function substitutePluginVariables(value, plugin) {
144921
144964
  let out = value.replace(/\$\{CLAUDE_PLUGIN_ROOT\}/g, () => normalize10(plugin.path));
144922
144965
  if (plugin.source) {
144923
144966
  const source = plugin.source;
144924
- out = out.replace(/\$\{CLAUDE_PLUGIN_DATA\}/g, () => normalize10(getPluginDataDir(source)));
144967
+ out = out.replace(/\$\{CLAUDE_PLUGIN_DATA\}/g, () => normalize10(plugin.dataPath ?? getPluginDataDir(source)));
144925
144968
  }
144926
144969
  return out;
144927
144970
  }
@@ -144955,7 +144998,10 @@ var init_pluginOptionsStorage = __esm(() => {
144955
144998
  init_settings2();
144956
144999
  init_mcpbHandler();
144957
145000
  init_pluginDirectories();
145001
+ init_state();
144958
145002
  loadPluginOptions = memoize_default((pluginId) => {
145003
+ if (tryGetExplicitPluginDataPath(pluginId))
145004
+ return {};
144959
145005
  const settings = getSettings_DEPRECATED();
144960
145006
  const nonSensitive = settings.pluginConfigs?.[pluginId]?.options ?? {};
144961
145007
  const storage = getSecureStorage();
@@ -145018,7 +145064,7 @@ async function loadMcpServersFromMcpb(plugin, mcpbPath, errors4) {
145018
145064
  }
145019
145065
  async function loadPluginMcpServers(plugin, errors4 = []) {
145020
145066
  let servers = {};
145021
- const defaultMcpServers = await loadMcpServersFromFile(plugin.path, PATH_SEGMENTS.settings.mcpProjectConfig);
145067
+ const defaultMcpServers = await loadMcpServersFromFile(plugin.path, PATH_SEGMENTS.settings.mcpProjectConfig, errors4, plugin, false);
145022
145068
  if (defaultMcpServers) {
145023
145069
  servers = { ...servers, ...defaultMcpServers };
145024
145070
  }
@@ -145031,7 +145077,7 @@ async function loadPluginMcpServers(plugin, errors4 = []) {
145031
145077
  servers = { ...servers, ...mcpbServers };
145032
145078
  }
145033
145079
  } else {
145034
- const mcpServers = await loadMcpServersFromFile(plugin.path, mcpServersSpec);
145080
+ const mcpServers = await loadMcpServersFromFile(plugin.path, mcpServersSpec, errors4, plugin, true);
145035
145081
  if (mcpServers) {
145036
145082
  servers = { ...servers, ...mcpServers };
145037
145083
  }
@@ -145043,11 +145089,18 @@ async function loadPluginMcpServers(plugin, errors4 = []) {
145043
145089
  if (isMcpbSource(spec)) {
145044
145090
  return await loadMcpServersFromMcpb(plugin, spec, errors4);
145045
145091
  }
145046
- return await loadMcpServersFromFile(plugin.path, spec);
145092
+ return await loadMcpServersFromFile(plugin.path, spec, errors4, plugin, true);
145047
145093
  }
145048
145094
  return spec;
145049
145095
  } catch (e) {
145050
145096
  logForDebugging2(`Failed to load MCP servers from spec for plugin ${plugin.name}: ${e}`, { level: "error" });
145097
+ errors4.push({
145098
+ type: "mcp-config-invalid",
145099
+ source: plugin.source,
145100
+ plugin: plugin.name,
145101
+ serverName: "manifest",
145102
+ validationError: errorMessage(e)
145103
+ });
145051
145104
  return null;
145052
145105
  }
145053
145106
  }));
@@ -145062,19 +145115,26 @@ async function loadPluginMcpServers(plugin, errors4 = []) {
145062
145115
  }
145063
145116
  return Object.keys(servers).length > 0 ? servers : undefined;
145064
145117
  }
145065
- async function loadMcpServersFromFile(pluginPath, relativePath) {
145118
+ async function loadMcpServersFromFile(pluginPath, relativePath, errors4, plugin, required2) {
145066
145119
  const fs2 = getFsImplementation();
145067
145120
  const filePath = join47(pluginPath, relativePath);
145068
145121
  let content;
145069
145122
  try {
145070
145123
  content = await fs2.readFile(filePath, { encoding: "utf-8" });
145071
145124
  } catch (e) {
145072
- if (isENOENT(e)) {
145125
+ if (isENOENT(e) && !required2) {
145073
145126
  return null;
145074
145127
  }
145075
145128
  logForDebugging2(`Failed to load MCP servers from ${filePath}: ${e}`, {
145076
145129
  level: "error"
145077
145130
  });
145131
+ errors4.push({
145132
+ type: "mcp-config-invalid",
145133
+ source: plugin.source,
145134
+ plugin: plugin.name,
145135
+ serverName: relativePath,
145136
+ validationError: errorMessage(e)
145137
+ });
145078
145138
  return null;
145079
145139
  }
145080
145140
  try {
@@ -145087,6 +145147,13 @@ async function loadMcpServersFromFile(pluginPath, relativePath) {
145087
145147
  validatedServers[name] = result.data;
145088
145148
  } else {
145089
145149
  logForDebugging2(`Invalid MCP server config for ${name} in ${filePath}: ${result.error.message}`, { level: "error" });
145150
+ errors4.push({
145151
+ type: "mcp-config-invalid",
145152
+ source: plugin.source,
145153
+ plugin: plugin.name,
145154
+ serverName: name,
145155
+ validationError: result.error.message
145156
+ });
145090
145157
  }
145091
145158
  }
145092
145159
  return validatedServers;
@@ -145094,6 +145161,13 @@ async function loadMcpServersFromFile(pluginPath, relativePath) {
145094
145161
  logForDebugging2(`Failed to load MCP servers from ${filePath}: ${error41}`, {
145095
145162
  level: "error"
145096
145163
  });
145164
+ errors4.push({
145165
+ type: "mcp-config-invalid",
145166
+ source: plugin.source,
145167
+ plugin: plugin.name,
145168
+ serverName: relativePath,
145169
+ validationError: errorMessage(error41)
145170
+ });
145097
145171
  return null;
145098
145172
  }
145099
145173
  }
@@ -145171,7 +145245,7 @@ function resolvePluginMcpEnvironment(config2, plugin, userConfig, errors4, plugi
145171
145245
  }
145172
145246
  const resolvedEnv = {
145173
145247
  CLAUDE_PLUGIN_ROOT: plugin.path,
145174
- CLAUDE_PLUGIN_DATA: getPluginDataDir(plugin.source),
145248
+ CLAUDE_PLUGIN_DATA: plugin.dataPath ?? getPluginDataDir(plugin.source),
145175
145249
  ...stdioConfig.env || {}
145176
145250
  };
145177
145251
  for (const [key, value] of Object.entries(resolvedEnv)) {
@@ -145633,16 +145707,16 @@ var init_walkPluginMarkdown = __esm(() => {
145633
145707
 
145634
145708
  // src/capabilities/plugins/loadPluginAgents.ts
145635
145709
  import { basename as basename9 } from "path";
145636
- async function loadAgentsFromDirectory(agentsPath, pluginName, sourceName, pluginPath, pluginManifest, loadedPaths) {
145710
+ async function loadAgentsFromDirectory(agentsPath, pluginName, sourceName, pluginPath, dataPath, pluginManifest, loadedPaths, strict = false) {
145637
145711
  const agents = [];
145638
145712
  await walkPluginMarkdown(agentsPath, async (fullPath, namespace) => {
145639
- const agent = await loadAgentFromFile(fullPath, pluginName, namespace, sourceName, pluginPath, pluginManifest, loadedPaths);
145713
+ const agent = await loadAgentFromFile(fullPath, pluginName, namespace, sourceName, pluginPath, dataPath, pluginManifest, loadedPaths, strict);
145640
145714
  if (agent)
145641
145715
  agents.push(agent);
145642
145716
  }, { logLabel: "agents" });
145643
145717
  return agents;
145644
145718
  }
145645
- async function loadAgentFromFile(filePath, pluginName, namespace, sourceName, pluginPath, pluginManifest, loadedPaths) {
145719
+ async function loadAgentFromFile(filePath, pluginName, namespace, sourceName, pluginPath, dataPath, pluginManifest, loadedPaths, strict = false) {
145646
145720
  const fs2 = getFsImplementation();
145647
145721
  if (isDuplicatePath(fs2, filePath, loadedPaths)) {
145648
145722
  return null;
@@ -145667,7 +145741,8 @@ async function loadAgentFromFile(filePath, pluginName, namespace, sourceName, pl
145667
145741
  const background = backgroundRaw === "true" || backgroundRaw === true ? true : undefined;
145668
145742
  let systemPrompt = substitutePluginVariables(markdownContent.trim(), {
145669
145743
  path: pluginPath,
145670
- source: sourceName
145744
+ source: sourceName,
145745
+ dataPath
145671
145746
  });
145672
145747
  if (pluginManifest.userConfig) {
145673
145748
  systemPrompt = substituteUserConfigInContent(systemPrompt, loadPluginOptions(sourceName), pluginManifest.userConfig);
@@ -145730,6 +145805,7 @@ async function loadAgentFromFile(filePath, pluginName, namespace, sourceName, pl
145730
145805
  color,
145731
145806
  model,
145732
145807
  filename: baseAgentName,
145808
+ sourcePath: filePath,
145733
145809
  plugin: sourceName,
145734
145810
  ...background ? { background } : {},
145735
145811
  ...memory ? { memory } : {},
@@ -145738,12 +145814,68 @@ async function loadAgentFromFile(filePath, pluginName, namespace, sourceName, pl
145738
145814
  ...maxTurns !== undefined ? { maxTurns } : {}
145739
145815
  };
145740
145816
  } catch (error41) {
145817
+ if (strict)
145818
+ throw error41;
145741
145819
  logForDebugging2(`Failed to load agent from ${filePath}: ${error41}`, {
145742
145820
  level: "error"
145743
145821
  });
145744
145822
  return null;
145745
145823
  }
145746
145824
  }
145825
+ async function loadPluginAgentsFromPlugins(enabled, options2 = {}) {
145826
+ const strict = options2.strict ?? false;
145827
+ const perPluginAgents = await Promise.all(enabled.map(async (plugin) => {
145828
+ const loadedPaths = new Set;
145829
+ const pluginAgents = [];
145830
+ if (plugin.agentsPath) {
145831
+ try {
145832
+ const agents = await loadAgentsFromDirectory(plugin.agentsPath, plugin.name, plugin.source, plugin.path, plugin.dataPath, plugin.manifest, loadedPaths, strict);
145833
+ pluginAgents.push(...agents);
145834
+ if (agents.length > 0) {
145835
+ logForDebugging2(`Loaded ${agents.length} agents from plugin ${plugin.name} default directory`);
145836
+ }
145837
+ } catch (error41) {
145838
+ if (strict)
145839
+ throw error41;
145840
+ logForDebugging2(`Failed to load agents from plugin ${plugin.name} default directory: ${error41}`, { level: "error" });
145841
+ }
145842
+ }
145843
+ if (plugin.agentsPaths) {
145844
+ const pathResults = await Promise.all(plugin.agentsPaths.map(async (agentPath) => {
145845
+ try {
145846
+ const fs2 = getFsImplementation();
145847
+ const stats = await fs2.stat(agentPath);
145848
+ if (stats.isDirectory()) {
145849
+ const agents = await loadAgentsFromDirectory(agentPath, plugin.name, plugin.source, plugin.path, plugin.dataPath, plugin.manifest, loadedPaths, strict);
145850
+ if (agents.length > 0) {
145851
+ logForDebugging2(`Loaded ${agents.length} agents from plugin ${plugin.name} custom path: ${agentPath}`);
145852
+ }
145853
+ return agents;
145854
+ } else if (stats.isFile() && agentPath.endsWith(".md")) {
145855
+ const agent = await loadAgentFromFile(agentPath, plugin.name, [], plugin.source, plugin.path, plugin.dataPath, plugin.manifest, loadedPaths, strict);
145856
+ if (agent) {
145857
+ logForDebugging2(`Loaded agent from plugin ${plugin.name} custom file: ${agentPath}`);
145858
+ return [agent];
145859
+ }
145860
+ }
145861
+ return [];
145862
+ } catch (error41) {
145863
+ if (strict)
145864
+ throw error41;
145865
+ logForDebugging2(`Failed to load agents from plugin ${plugin.name} custom path ${agentPath}: ${error41}`, { level: "error" });
145866
+ return [];
145867
+ }
145868
+ }));
145869
+ for (const agents of pathResults) {
145870
+ pluginAgents.push(...agents);
145871
+ }
145872
+ }
145873
+ return pluginAgents;
145874
+ }));
145875
+ const allAgents = perPluginAgents.flat();
145876
+ logForDebugging2(`Total plugin agents loaded: ${allAgents.length}`);
145877
+ return allAgents;
145878
+ }
145747
145879
  function clearPluginAgentCache() {
145748
145880
  loadPluginAgents.cache?.clear?.();
145749
145881
  }
@@ -145766,53 +145898,7 @@ var init_loadPluginAgents = __esm(() => {
145766
145898
  if (errors4.length > 0) {
145767
145899
  logForDebugging2(`Plugin loading errors: ${errors4.map((e) => getPluginErrorMessage(e)).join(", ")}`);
145768
145900
  }
145769
- const perPluginAgents = await Promise.all(enabled.map(async (plugin) => {
145770
- const loadedPaths = new Set;
145771
- const pluginAgents = [];
145772
- if (plugin.agentsPath) {
145773
- try {
145774
- const agents = await loadAgentsFromDirectory(plugin.agentsPath, plugin.name, plugin.source, plugin.path, plugin.manifest, loadedPaths);
145775
- pluginAgents.push(...agents);
145776
- if (agents.length > 0) {
145777
- logForDebugging2(`Loaded ${agents.length} agents from plugin ${plugin.name} default directory`);
145778
- }
145779
- } catch (error41) {
145780
- logForDebugging2(`Failed to load agents from plugin ${plugin.name} default directory: ${error41}`, { level: "error" });
145781
- }
145782
- }
145783
- if (plugin.agentsPaths) {
145784
- const pathResults = await Promise.all(plugin.agentsPaths.map(async (agentPath) => {
145785
- try {
145786
- const fs2 = getFsImplementation();
145787
- const stats = await fs2.stat(agentPath);
145788
- if (stats.isDirectory()) {
145789
- const agents = await loadAgentsFromDirectory(agentPath, plugin.name, plugin.source, plugin.path, plugin.manifest, loadedPaths);
145790
- if (agents.length > 0) {
145791
- logForDebugging2(`Loaded ${agents.length} agents from plugin ${plugin.name} custom path: ${agentPath}`);
145792
- }
145793
- return agents;
145794
- } else if (stats.isFile() && agentPath.endsWith(".md")) {
145795
- const agent = await loadAgentFromFile(agentPath, plugin.name, [], plugin.source, plugin.path, plugin.manifest, loadedPaths);
145796
- if (agent) {
145797
- logForDebugging2(`Loaded agent from plugin ${plugin.name} custom file: ${agentPath}`);
145798
- return [agent];
145799
- }
145800
- }
145801
- return [];
145802
- } catch (error41) {
145803
- logForDebugging2(`Failed to load agents from plugin ${plugin.name} custom path ${agentPath}: ${error41}`, { level: "error" });
145804
- return [];
145805
- }
145806
- }));
145807
- for (const agents of pathResults) {
145808
- pluginAgents.push(...agents);
145809
- }
145810
- }
145811
- return pluginAgents;
145812
- }));
145813
- const allAgents = perPluginAgents.flat();
145814
- logForDebugging2(`Total plugin agents loaded: ${allAgents.length}`);
145815
- return allAgents;
145901
+ return loadPluginAgentsFromPlugins(enabled);
145816
145902
  });
145817
145903
  });
145818
145904
 
@@ -146485,6 +146571,12 @@ function mergeAgentsByType(base2, override) {
146485
146571
  byType.set(agent.agentType, agent);
146486
146572
  return [...byType.values()];
146487
146573
  }
146574
+ function withDefaultAgentForInvocation(activeAgents, requestedType, defaultAgent) {
146575
+ if (requestedType !== undefined || activeAgents.some((agent) => agent.agentType === defaultAgent.agentType)) {
146576
+ return activeAgents;
146577
+ }
146578
+ return [...activeAgents, defaultAgent];
146579
+ }
146488
146580
 
146489
146581
  // src/capabilities/tools/AgentTool/builtInAgents.ts
146490
146582
  var exports_builtInAgents = {};
@@ -240254,10 +240346,23 @@ function deepOmitNullProps(value) {
240254
240346
  }
240255
240347
  return value;
240256
240348
  }
240257
- function safeParseToolInputWithNullCoercion(schema, input) {
240349
+ function containsUnrecognizedKeysIssue(value) {
240350
+ if (Array.isArray(value))
240351
+ return value.some(containsUnrecognizedKeysIssue);
240352
+ if (value === null || typeof value !== "object")
240353
+ return false;
240354
+ const issue2 = value;
240355
+ if (issue2.code === "unrecognized_keys")
240356
+ return true;
240357
+ return containsUnrecognizedKeysIssue(issue2.errors);
240358
+ }
240359
+ function safeParseToolInputWithNullCoercion(schema, input, unknownKeys = "strip") {
240258
240360
  const first = schema.safeParse(input);
240259
240361
  if (first.success)
240260
240362
  return first;
240363
+ if (unknownKeys === "reject" && containsUnrecognizedKeysIssue(first.error.issues)) {
240364
+ return first;
240365
+ }
240261
240366
  if (input === null || typeof input !== "object") {
240262
240367
  return first;
240263
240368
  }
@@ -240743,6 +240848,54 @@ function getRuleBehaviorDescription(permissionResult) {
240743
240848
  }
240744
240849
  }
240745
240850
 
240851
+ // src/controller/dispatch/permissionPreDecision.ts
240852
+ function startPermissionPreDecisions(blocks, assistantMessages, canUseTool, toolUseContext) {
240853
+ const existing = toolUseContext.permissionPreDecisions;
240854
+ if (existing && existing.size > 0) {
240855
+ return;
240856
+ }
240857
+ const preDecisions = new Map;
240858
+ toolUseContext.permissionPreDecisions = preDecisions;
240859
+ for (const block2 of blocks) {
240860
+ const tool = findToolRuntimeByName(toolUseContext.options.tools, block2.name);
240861
+ if (!tool) {
240862
+ continue;
240863
+ }
240864
+ const parsedInput = safeParseToolInputWithNullCoercion(tool.inputSchema, block2.input, tool.unknownKeys);
240865
+ if (!parsedInput.success) {
240866
+ continue;
240867
+ }
240868
+ const assistantMessage = assistantMessages.find((message) => message.message.content.some((content) => content.type === "tool_use" && content.id === block2.id));
240869
+ if (!assistantMessage) {
240870
+ continue;
240871
+ }
240872
+ let input = parsedInput.data;
240873
+ if (tool.backfillObservableInput && typeof input === "object" && input !== null) {
240874
+ input = { ...input };
240875
+ tool.backfillObservableInput(input);
240876
+ }
240877
+ const promise3 = canUseTool(tool, input, toolUseContext, assistantMessage, block2.id);
240878
+ promise3.catch(() => {});
240879
+ preDecisions.set(block2.id, { input, promise: promise3 });
240880
+ }
240881
+ }
240882
+ function consumePermissionPreDecision(toolUseContext, toolUseID, input, fallback) {
240883
+ const cache2 = toolUseContext.permissionPreDecisions;
240884
+ const entry = cache2?.get(toolUseID);
240885
+ if (!cache2 || !entry) {
240886
+ return fallback();
240887
+ }
240888
+ cache2.delete(toolUseID);
240889
+ if (jsonStringify(entry.input) !== jsonStringify(input)) {
240890
+ return fallback();
240891
+ }
240892
+ return entry.promise;
240893
+ }
240894
+ var init_permissionPreDecision = __esm(() => {
240895
+ init_toolRuntime();
240896
+ init_slowOperations();
240897
+ });
240898
+
240746
240899
  // src/controller/dispatch/toolHooks.ts
240747
240900
  async function* runPostToolUseHooks(toolUseContext, tool, toolUseID, messageId, toolInput, toolResponse, requestId, mcpServerType, mcpServerBaseUrl) {
240748
240901
  const postToolStartTime = Date.now();
@@ -240930,7 +241083,7 @@ async function resolveHookPermissionDecision(hookPermissionResult, tool, input,
240930
241083
  if (requiresInteraction && !interactionSatisfied || requireCanUseTool) {
240931
241084
  logForDebugging2(`Hook approved tool use for ${tool.name}, but canUseTool is required`);
240932
241085
  return {
240933
- decision: await canUseTool(tool, hookInput, toolUseContext, assistantMessage, toolUseID),
241086
+ decision: await consumePermissionPreDecision(toolUseContext, toolUseID, hookInput, () => canUseTool(tool, hookInput, toolUseContext, assistantMessage, toolUseID)),
240934
241087
  input: hookInput
240935
241088
  };
240936
241089
  }
@@ -240945,7 +241098,7 @@ async function resolveHookPermissionDecision(hookPermissionResult, tool, input,
240945
241098
  }
240946
241099
  logForDebugging2(`Hook approved tool use for ${tool.name}, but ask rule requires prompt`);
240947
241100
  return {
240948
- decision: await canUseTool(tool, hookInput, toolUseContext, assistantMessage, toolUseID),
241101
+ decision: await consumePermissionPreDecision(toolUseContext, toolUseID, hookInput, () => canUseTool(tool, hookInput, toolUseContext, assistantMessage, toolUseID)),
240949
241102
  input: hookInput
240950
241103
  };
240951
241104
  }
@@ -240955,8 +241108,9 @@ async function resolveHookPermissionDecision(hookPermissionResult, tool, input,
240955
241108
  }
240956
241109
  const forceDecision = hookPermissionResult?.behavior === "ask" ? hookPermissionResult : undefined;
240957
241110
  const askInput = hookPermissionResult?.behavior === "ask" && hookPermissionResult.updatedInput ? hookPermissionResult.updatedInput : input;
241111
+ const decision = forceDecision ? await canUseTool(tool, askInput, toolUseContext, assistantMessage, toolUseID, forceDecision) : await consumePermissionPreDecision(toolUseContext, toolUseID, askInput, () => canUseTool(tool, askInput, toolUseContext, assistantMessage, toolUseID));
240958
241112
  return {
240959
- decision: await canUseTool(tool, askInput, toolUseContext, assistantMessage, toolUseID, forceDecision),
241113
+ decision,
240960
241114
  input: askInput
240961
241115
  };
240962
241116
  }
@@ -241117,6 +241271,7 @@ var init_toolHooks = __esm(() => {
241117
241271
  init_permissions2();
241118
241272
  init_toolErrors();
241119
241273
  init_utils5();
241274
+ init_permissionPreDecision();
241120
241275
  });
241121
241276
 
241122
241277
  // src/controller/dispatch/toolExecution.ts
@@ -241372,9 +241527,8 @@ function streamedCheckPermissionsAndCallTool(tool, toolUseID, input, toolUseCont
241372
241527
  return stream4;
241373
241528
  }
241374
241529
  async function checkPermissionsAndCallTool(tool, toolUseID, input, toolUseContext, canUseTool, assistantMessage, messageId, requestId, mcpServerType, mcpServerBaseUrl, onToolProgress) {
241375
- const parsedInput = safeParseToolInputWithNullCoercion(tool.inputSchema, input);
241376
- if (!parsedInput.success) {
241377
- let errorContent = formatZodValidationError(tool.name, parsedInput.error);
241530
+ const inputValidationFailure = (error41) => {
241531
+ let errorContent = formatZodValidationError(tool.name, error41);
241378
241532
  const schemaHint = buildSchemaNotSentHint(tool, toolUseContext.messages, toolUseContext.options.tools);
241379
241533
  if (schemaHint) {
241380
241534
  logEvent("tengu_deferred_tool_schema_not_sent", {
@@ -241414,11 +241568,15 @@ async function checkPermissionsAndCallTool(tool, toolUseID, input, toolUseContex
241414
241568
  tool_use_id: toolUseID
241415
241569
  }
241416
241570
  ],
241417
- toolUseResult: `InputValidationError: ${parsedInput.error.message}`,
241571
+ toolUseResult: `InputValidationError: ${error41.message}`,
241418
241572
  sourceToolAssistantUUID: assistantMessage.uuid
241419
241573
  })
241420
241574
  }
241421
241575
  ];
241576
+ };
241577
+ const parsedInput = safeParseToolInputWithNullCoercion(tool.inputSchema, input, tool.unknownKeys);
241578
+ if (!parsedInput.success) {
241579
+ return inputValidationFailure(parsedInput.error);
241422
241580
  }
241423
241581
  const isValidCall = await tool.validateInput?.(parsedInput.data, toolUseContext);
241424
241582
  if (isValidCall?.result === false) {
@@ -241654,6 +241812,16 @@ async function checkPermissionsAndCallTool(tool, toolUseID, input, toolUseContex
241654
241812
  if (permissionDecision.updatedInput !== undefined) {
241655
241813
  processedInput = permissionDecision.updatedInput;
241656
241814
  }
241815
+ if (tool.unknownKeys === "reject") {
241816
+ const finalInput = safeParseToolInputWithNullCoercion(tool.inputSchema, processedInput, tool.unknownKeys);
241817
+ if (!finalInput.success) {
241818
+ endToolBlockedOnUserSpan("reject", "input-validation");
241819
+ endToolSpan();
241820
+ resultingMessages.push(...inputValidationFailure(finalInput.error));
241821
+ return resultingMessages;
241822
+ }
241823
+ processedInput = finalInput.data;
241824
+ }
241657
241825
  const telemetryToolInput = extractToolInputForTelemetry(processedInput);
241658
241826
  let toolParameters = {};
241659
241827
  if (isToolDetailsLoggingEnabled()) {
@@ -242616,6 +242784,9 @@ function getMaxToolUseConcurrency() {
242616
242784
  return parseInt(resolveEnvVar("MAX_TOOL_USE_CONCURRENCY") || "", 10) || 10;
242617
242785
  }
242618
242786
  async function* runTools(toolUseMessages, assistantMessages, canUseTool, toolUseContext) {
242787
+ if (toolUseContext.options.preDecidePermissions) {
242788
+ startPermissionPreDecisions(toolUseMessages, assistantMessages, canUseTool, toolUseContext);
242789
+ }
242619
242790
  let currentContext = toolUseContext;
242620
242791
  for (const { isConcurrencySafe, blocks } of partitionToolCalls(toolUseMessages, currentContext)) {
242621
242792
  if (isConcurrencySafe) {
@@ -242709,6 +242880,7 @@ var init_toolOrchestration = __esm(() => {
242709
242880
  init_toolRuntime();
242710
242881
  init_generators();
242711
242882
  init_toolExecution();
242883
+ init_permissionPreDecision();
242712
242884
  init_state();
242713
242885
  });
242714
242886
 
@@ -244805,7 +244977,7 @@ function getAnthropicEnvMetadata() {
244805
244977
  function getBuildAgeMinutes() {
244806
244978
  if (false)
244807
244979
  ;
244808
- const buildTime = new Date("2026-08-21T04:07:58.719Z").getTime();
244980
+ const buildTime = new Date("2026-09-03T09:12:13.936Z").getTime();
244809
244981
  if (isNaN(buildTime))
244810
244982
  return;
244811
244983
  return Math.floor((Date.now() - buildTime) / 60000);
@@ -245335,6 +245507,7 @@ function createSubagentContext(parentContext, overrides) {
245335
245507
  dynamicSkillDirTriggers: new Set,
245336
245508
  discoveredSkillNames: new Set,
245337
245509
  toolDecisions: undefined,
245510
+ permissionPreDecisions: undefined,
245338
245511
  contentReplacementState: overrides?.contentReplacementState ?? (parentContext.contentReplacementState ? cloneContentReplacementState(parentContext.contentReplacementState) : undefined),
245339
245512
  abortController,
245340
245513
  getAppState,
@@ -248589,6 +248762,31 @@ async function* runAgent({
248589
248762
  level: "warn"
248590
248763
  });
248591
248764
  });
248765
+ let partialBaseMessage = null;
248766
+ const partialTextByIndex = new Map;
248767
+ const PARTIAL_PROGRESS_INTERVAL_MS = 50;
248768
+ let lastPartialAssistantAt = 0;
248769
+ let lastPartialProgressHookAt = 0;
248770
+ let foregroundSkipped = 0;
248771
+ let backgroundSkipped = 0;
248772
+ const logPartialProgress = (reason, chars, foregroundEmitted, backgroundEmitted) => {
248773
+ logForDebugging2(`[StreamThrottle:SubAgent] ${JSON.stringify({
248774
+ reason,
248775
+ agentId,
248776
+ agentType: agentDefinition.agentType,
248777
+ messageId: partialBaseMessage?.id ?? null,
248778
+ intervalMs: PARTIAL_PROGRESS_INTERVAL_MS,
248779
+ chars,
248780
+ foregroundEmitted,
248781
+ foregroundSkipped,
248782
+ backgroundEmitted,
248783
+ backgroundSkipped
248784
+ })}`);
248785
+ if (foregroundEmitted)
248786
+ foregroundSkipped = 0;
248787
+ if (backgroundEmitted)
248788
+ backgroundSkipped = 0;
248789
+ };
248592
248790
  try {
248593
248791
  const additionalContexts = [];
248594
248792
  for await (const hookResult of executeSubagentStartHooks(agentId, agentDefinition.agentType, agentAbortController.signal, undefined, toolUseContext.toolUseId, isAsync2)) {
@@ -248696,10 +248894,6 @@ async function* runAgent({
248696
248894
  ...description && { description }
248697
248895
  }).catch((_err) => logForDebugging2(`Failed to write agent metadata: ${_err}`));
248698
248896
  let lastRecordedUuid = initialMessages.at(-1)?.uuid ?? null;
248699
- let partialBaseMessage = null;
248700
- const partialTextByIndex = new Map;
248701
- const PARTIAL_PROGRESS_HOOK_INTERVAL_MS = 100;
248702
- let lastPartialProgressHookAt = 0;
248703
248897
  const agentExtraBody = agentDefinition.extraBody;
248704
248898
  const agentQuery = query({
248705
248899
  messages: initialMessages,
@@ -248724,6 +248918,11 @@ async function* runAgent({
248724
248918
  if (message.type === "stream_event") {
248725
248919
  const ev = message.event;
248726
248920
  if (ev.type === "message_start") {
248921
+ if (foregroundSkipped > 0 || backgroundSkipped > 0) {
248922
+ logPartialProgress("message-start", 0, false, false);
248923
+ foregroundSkipped = 0;
248924
+ backgroundSkipped = 0;
248925
+ }
248727
248926
  if (message.ttftMs != null) {
248728
248927
  toolUseContext.pushApiMetricsEntry?.(message.ttftMs);
248729
248928
  }
@@ -248735,22 +248934,36 @@ async function* runAgent({
248735
248934
  const idx = ev.index ?? 0;
248736
248935
  const acc = (partialTextByIndex.get(idx) ?? "") + ev.delta.text;
248737
248936
  partialTextByIndex.set(idx, acc);
248738
- onPartialAssistant?.({
248739
- type: "assistant",
248740
- message: {
248741
- ...partialBaseMessage,
248742
- content: [{ type: "text", text: acc, citations: null }]
248743
- },
248744
- uuid: randomUUID10(),
248745
- timestamp: new Date().toISOString()
248746
- });
248937
+ const now = Date.now();
248938
+ let foregroundEmitted = false;
248939
+ let backgroundEmitted = false;
248940
+ if (onPartialAssistant && now - lastPartialAssistantAt >= PARTIAL_PROGRESS_INTERVAL_MS) {
248941
+ lastPartialAssistantAt = now;
248942
+ foregroundEmitted = true;
248943
+ onPartialAssistant({
248944
+ type: "assistant",
248945
+ message: {
248946
+ ...partialBaseMessage,
248947
+ content: [{ type: "text", text: acc, citations: null }]
248948
+ },
248949
+ uuid: randomUUID10(),
248950
+ timestamp: new Date().toISOString()
248951
+ });
248952
+ } else if (onPartialAssistant) {
248953
+ foregroundSkipped += 1;
248954
+ }
248747
248955
  if (isAsync2) {
248748
- const now = Date.now();
248749
- if (now - lastPartialProgressHookAt >= PARTIAL_PROGRESS_HOOK_INTERVAL_MS) {
248956
+ if (now - lastPartialProgressHookAt >= PARTIAL_PROGRESS_INTERVAL_MS) {
248750
248957
  lastPartialProgressHookAt = now;
248958
+ backgroundEmitted = true;
248751
248959
  executeSubagentProgressHooks(agentId, agentDefinition.agentType, partialBaseMessage.id, toolUseContext.toolUseId, [{ type: "text", text: acc }]).catch(() => {});
248960
+ } else {
248961
+ backgroundSkipped += 1;
248752
248962
  }
248753
248963
  }
248964
+ if (foregroundEmitted || backgroundEmitted) {
248965
+ logPartialProgress("emit", acc.length, foregroundEmitted, backgroundEmitted);
248966
+ }
248754
248967
  }
248755
248968
  continue;
248756
248969
  }
@@ -248799,6 +249012,9 @@ async function* runAgent({
248799
249012
  agentRunError = err2;
248800
249013
  throw err2;
248801
249014
  } finally {
249015
+ if (foregroundSkipped > 0 || backgroundSkipped > 0) {
249016
+ logPartialProgress("finalize", 0, false, false);
249017
+ }
248802
249018
  await finalizeLifecycle([
248803
249019
  async () => {
248804
249020
  const naturalStopAlreadyFired = isAsync2 && hasSubagentStopFired(agentId);
@@ -265509,7 +265725,7 @@ var init_AgentTool = __esm(() => {
265509
265725
  }
265510
265726
  selectedAgent = FORK_AGENT;
265511
265727
  } else {
265512
- const allAgents = toolUseContext.options.agentDefinitions.activeAgents;
265728
+ const allAgents = withDefaultAgentForInvocation(toolUseContext.options.agentDefinitions.activeAgents, subagent_type, GENERAL_PURPOSE_AGENT);
265513
265729
  const {
265514
265730
  allowedAgentTypes
265515
265731
  } = toolUseContext.options.agentDefinitions;
@@ -266822,7 +267038,7 @@ function resolvePluginLspEnvironment(config2, plugin, userConfig, _errors) {
266822
267038
  }
266823
267039
  const resolvedEnv = {
266824
267040
  CLAUDE_PLUGIN_ROOT: plugin.path,
266825
- CLAUDE_PLUGIN_DATA: getPluginDataDir(plugin.source),
267041
+ CLAUDE_PLUGIN_DATA: plugin.dataPath ?? getPluginDataDir(plugin.source),
266826
267042
  ...resolved.env || {}
266827
267043
  };
266828
267044
  for (const [key, value] of Object.entries(resolvedEnv)) {
@@ -270678,14 +270894,14 @@ var init_LSPServerInstance = __esm(() => {
270678
270894
  // src/capabilities/lsp/LSPServerManager.ts
270679
270895
  import * as path12 from "path";
270680
270896
  import { pathToFileURL as pathToFileURL2 } from "url";
270681
- function createLSPServerManager() {
270897
+ function createLSPServerManager(explicitServerConfigs) {
270682
270898
  const servers = new Map;
270683
270899
  const extensionMap = new Map;
270684
270900
  const openedFiles = new Map;
270685
270901
  async function initialize3() {
270686
270902
  let serverConfigs;
270687
270903
  try {
270688
- const result = await getAllLspServers();
270904
+ const result = explicitServerConfigs ? { servers: { ...explicitServerConfigs } } : await getAllLspServers();
270689
270905
  serverConfigs = result.servers;
270690
270906
  logForDebugging2(`[LSP SERVER MANAGER] getAllLspServers returned ${Object.keys(serverConfigs).length} server(s)`);
270691
270907
  } catch (error41) {
@@ -271050,6 +271266,9 @@ var init_passiveFeedback = __esm(() => {
271050
271266
 
271051
271267
  // src/capabilities/lsp/manager.ts
271052
271268
  function getLspServerManager() {
271269
+ const sessionManager = tryGetSessionLspManager();
271270
+ if (sessionManager)
271271
+ return sessionManager;
271053
271272
  if (initializationState === "failed") {
271054
271273
  return;
271055
271274
  }
@@ -271071,8 +271290,6 @@ function getInitializationStatus() {
271071
271290
  return { status: "success" };
271072
271291
  }
271073
271292
  function isLspConnected() {
271074
- if (initializationState === "failed")
271075
- return false;
271076
271293
  const manager = getLspServerManager();
271077
271294
  if (!manager)
271078
271295
  return false;
@@ -271170,6 +271387,7 @@ var init_manager = __esm(() => {
271170
271387
  init_log3();
271171
271388
  init_LSPServerManager();
271172
271389
  init_passiveFeedback();
271390
+ init_registries2();
271173
271391
  });
271174
271392
 
271175
271393
  // src/capabilities/tools/shared/teamMemorySync/teamMemSecretGuard.ts
@@ -284046,20 +284264,20 @@ function transformPluginSkillFiles(files) {
284046
284264
  }
284047
284265
  return result;
284048
284266
  }
284049
- async function loadCommandsFromDirectory(commandsPath, pluginName, sourceName, pluginManifest, pluginPath, config2 = { isSkillMode: false }, loadedPaths = new Set) {
284267
+ async function loadCommandsFromDirectory(commandsPath, pluginName, sourceName, pluginManifest, pluginPath, config2 = { isSkillMode: false }, loadedPaths = new Set, pluginDataPath, strict = false) {
284050
284268
  const markdownFiles = await collectMarkdownFiles(commandsPath, commandsPath, loadedPaths);
284051
284269
  const processedFiles = transformPluginSkillFiles(markdownFiles);
284052
284270
  const commands = [];
284053
284271
  for (const file2 of processedFiles) {
284054
284272
  const commandName = getCommandNameFromFile(file2.filePath, file2.baseDir, pluginName);
284055
- const command = createPluginCommand(commandName, file2, sourceName, pluginManifest, pluginPath, isSkillFile(file2.filePath), config2);
284273
+ const command = createPluginCommand(commandName, file2, sourceName, pluginManifest, pluginPath, isSkillFile(file2.filePath), config2, pluginDataPath, strict);
284056
284274
  if (command) {
284057
284275
  commands.push(command);
284058
284276
  }
284059
284277
  }
284060
284278
  return commands;
284061
284279
  }
284062
- function createPluginCommand(commandName, file2, sourceName, pluginManifest, pluginPath, isSkill, config2 = { isSkillMode: false }) {
284280
+ function createPluginCommand(commandName, file2, sourceName, pluginManifest, pluginPath, isSkill, config2 = { isSkillMode: false }, pluginDataPath, strict = false) {
284063
284281
  try {
284064
284282
  const { frontmatter, content } = file2;
284065
284283
  const validatedDescription = coerceDescriptionToString(frontmatter.description, commandName);
@@ -284067,10 +284285,12 @@ function createPluginCommand(commandName, file2, sourceName, pluginManifest, plu
284067
284285
  const rawAllowedTools = frontmatter["allowed-tools"];
284068
284286
  const substitutedAllowedTools = typeof rawAllowedTools === "string" ? substitutePluginVariables(rawAllowedTools, {
284069
284287
  path: pluginPath,
284070
- source: sourceName
284288
+ source: sourceName,
284289
+ dataPath: pluginDataPath
284071
284290
  }) : Array.isArray(rawAllowedTools) ? rawAllowedTools.map((tool) => typeof tool === "string" ? substitutePluginVariables(tool, {
284072
284291
  path: pluginPath,
284073
- source: sourceName
284292
+ source: sourceName,
284293
+ dataPath: pluginDataPath
284074
284294
  }) : tool) : rawAllowedTools;
284075
284295
  const allowedTools = parseSlashCommandToolsFromFrontmatter(substitutedAllowedTools);
284076
284296
  const argumentHint = frontmatter["argument-hint"];
@@ -284091,6 +284311,7 @@ function createPluginCommand(commandName, file2, sourceName, pluginManifest, plu
284091
284311
  return {
284092
284312
  type: "prompt",
284093
284313
  name: commandName,
284314
+ sourcePath: file2.filePath,
284094
284315
  description,
284095
284316
  hasUserSpecifiedDescription: validatedDescription !== null,
284096
284317
  allowedTools,
@@ -284115,13 +284336,20 @@ function createPluginCommand(commandName, file2, sourceName, pluginManifest, plu
284115
284336
  return displayName || commandName;
284116
284337
  },
284117
284338
  async getPromptForCommand(args, context4) {
284118
- let finalContent = config2.isSkillMode ? `Base directory for this skill: ${dirname29(file2.filePath)}
284339
+ const sourceContext = [
284340
+ `Source file: ${file2.filePath}`,
284341
+ `Plugin root: ${pluginPath}`,
284342
+ ...config2.isSkillMode ? [`Base directory for this skill: ${dirname29(file2.filePath)}`] : []
284343
+ ];
284344
+ let finalContent = `${sourceContext.join(`
284345
+ `)}
284119
284346
 
284120
- ${content}` : content;
284347
+ ${content}`;
284121
284348
  finalContent = substituteArguments(finalContent, args, true, argumentNames);
284122
284349
  finalContent = substitutePluginVariables(finalContent, {
284123
284350
  path: pluginPath,
284124
- source: sourceName
284351
+ source: sourceName,
284352
+ dataPath: pluginDataPath
284125
284353
  });
284126
284354
  if (pluginManifest.userConfig) {
284127
284355
  finalContent = substituteUserConfigInContent(finalContent, loadPluginOptions(sourceName), pluginManifest.userConfig);
@@ -284152,16 +284380,161 @@ ${content}` : content;
284152
284380
  }
284153
284381
  };
284154
284382
  } catch (error41) {
284383
+ if (strict)
284384
+ throw error41;
284155
284385
  logForDebugging2(`Failed to create command from ${file2.filePath}: ${error41}`, {
284156
284386
  level: "error"
284157
284387
  });
284158
284388
  return null;
284159
284389
  }
284160
284390
  }
284391
+ async function loadPluginCommandsFromPlugins(enabled, options2 = {}) {
284392
+ const strict = options2.strict ?? false;
284393
+ const perPluginCommands = await Promise.all(enabled.map(async (plugin) => {
284394
+ const loadedPaths = new Set;
284395
+ const pluginCommands = [];
284396
+ if (plugin.commandsPath) {
284397
+ try {
284398
+ const commands = await loadCommandsFromDirectory(plugin.commandsPath, plugin.name, plugin.source, plugin.manifest, plugin.path, { isSkillMode: false }, loadedPaths, plugin.dataPath, strict);
284399
+ pluginCommands.push(...commands);
284400
+ if (commands.length > 0) {
284401
+ logForDebugging2(`Loaded ${commands.length} commands from plugin ${plugin.name} default directory`);
284402
+ }
284403
+ } catch (error41) {
284404
+ if (strict)
284405
+ throw error41;
284406
+ logForDebugging2(`Failed to load commands from plugin ${plugin.name} default directory: ${error41}`, { level: "error" });
284407
+ }
284408
+ }
284409
+ if (plugin.commandsPaths) {
284410
+ logForDebugging2(`Plugin ${plugin.name} has commandsPaths: ${plugin.commandsPaths.join(", ")}`);
284411
+ const pathResults = await Promise.all(plugin.commandsPaths.map(async (commandPath) => {
284412
+ try {
284413
+ const fs2 = getFsImplementation();
284414
+ const stats = await fs2.stat(commandPath);
284415
+ logForDebugging2(`Checking commandPath ${commandPath} - isDirectory: ${stats.isDirectory()}, isFile: ${stats.isFile()}`);
284416
+ if (stats.isDirectory()) {
284417
+ const commands = await loadCommandsFromDirectory(commandPath, plugin.name, plugin.source, plugin.manifest, plugin.path, { isSkillMode: false }, loadedPaths, plugin.dataPath, strict);
284418
+ if (commands.length > 0) {
284419
+ logForDebugging2(`Loaded ${commands.length} commands from plugin ${plugin.name} custom path: ${commandPath}`);
284420
+ } else {
284421
+ logForDebugging2(`Warning: No commands found in plugin ${plugin.name} custom directory: ${commandPath}. Expected .md files or SKILL.md in subdirectories.`, { level: "warn" });
284422
+ }
284423
+ return commands;
284424
+ } else if (stats.isFile() && commandPath.endsWith(".md")) {
284425
+ if (isDuplicatePath(fs2, commandPath, loadedPaths)) {
284426
+ return [];
284427
+ }
284428
+ const content = await fs2.readFile(commandPath, {
284429
+ encoding: "utf-8"
284430
+ });
284431
+ const { frontmatter, content: markdownContent } = parseFrontmatter(content, commandPath);
284432
+ let commandName;
284433
+ let metadataOverride;
284434
+ if (plugin.commandsMetadata) {
284435
+ for (const [name, metadata] of Object.entries(plugin.commandsMetadata)) {
284436
+ if (metadata.source) {
284437
+ const fullMetadataPath = join62(plugin.path, metadata.source);
284438
+ if (commandPath === fullMetadataPath) {
284439
+ commandName = `${plugin.name}:${name}`;
284440
+ metadataOverride = metadata;
284441
+ break;
284442
+ }
284443
+ }
284444
+ }
284445
+ }
284446
+ if (!commandName) {
284447
+ commandName = `${plugin.name}:${basename16(commandPath).replace(/\.md$/, "")}`;
284448
+ }
284449
+ const finalFrontmatter = metadataOverride ? {
284450
+ ...frontmatter,
284451
+ ...metadataOverride.description && {
284452
+ description: metadataOverride.description
284453
+ },
284454
+ ...metadataOverride.argumentHint && {
284455
+ "argument-hint": metadataOverride.argumentHint
284456
+ },
284457
+ ...metadataOverride.model && {
284458
+ model: metadataOverride.model
284459
+ },
284460
+ ...metadataOverride.allowedTools && {
284461
+ "allowed-tools": metadataOverride.allowedTools.join(",")
284462
+ }
284463
+ } : frontmatter;
284464
+ const file2 = {
284465
+ filePath: commandPath,
284466
+ baseDir: dirname29(commandPath),
284467
+ frontmatter: finalFrontmatter,
284468
+ content: markdownContent
284469
+ };
284470
+ const command = createPluginCommand(commandName, file2, plugin.source, plugin.manifest, plugin.path, false, { isSkillMode: false }, plugin.dataPath, strict);
284471
+ if (command) {
284472
+ logForDebugging2(`Loaded command from plugin ${plugin.name} custom file: ${commandPath}${metadataOverride ? " (with metadata override)" : ""}`);
284473
+ return [command];
284474
+ }
284475
+ }
284476
+ return [];
284477
+ } catch (error41) {
284478
+ if (strict)
284479
+ throw error41;
284480
+ logForDebugging2(`Failed to load commands from plugin ${plugin.name} custom path ${commandPath}: ${error41}`, { level: "error" });
284481
+ return [];
284482
+ }
284483
+ }));
284484
+ for (const commands of pathResults) {
284485
+ pluginCommands.push(...commands);
284486
+ }
284487
+ }
284488
+ if (plugin.commandsMetadata) {
284489
+ for (const [name, metadata] of Object.entries(plugin.commandsMetadata)) {
284490
+ if (metadata.content && !metadata.source) {
284491
+ try {
284492
+ const { frontmatter, content: markdownContent } = parseFrontmatter(metadata.content, `<inline:${plugin.name}:${name}>`);
284493
+ const finalFrontmatter = {
284494
+ ...frontmatter,
284495
+ ...metadata.description && {
284496
+ description: metadata.description
284497
+ },
284498
+ ...metadata.argumentHint && {
284499
+ "argument-hint": metadata.argumentHint
284500
+ },
284501
+ ...metadata.model && {
284502
+ model: metadata.model
284503
+ },
284504
+ ...metadata.allowedTools && {
284505
+ "allowed-tools": metadata.allowedTools.join(",")
284506
+ }
284507
+ };
284508
+ const commandName = `${plugin.name}:${name}`;
284509
+ const file2 = {
284510
+ filePath: `<inline:${commandName}>`,
284511
+ baseDir: plugin.path,
284512
+ frontmatter: finalFrontmatter,
284513
+ content: markdownContent
284514
+ };
284515
+ const command = createPluginCommand(commandName, file2, plugin.source, plugin.manifest, plugin.path, false, { isSkillMode: false }, plugin.dataPath, strict);
284516
+ if (command) {
284517
+ pluginCommands.push(command);
284518
+ logForDebugging2(`Loaded inline content command from plugin ${plugin.name}: ${commandName}`);
284519
+ }
284520
+ } catch (error41) {
284521
+ if (strict)
284522
+ throw error41;
284523
+ logForDebugging2(`Failed to load inline content command ${name} from plugin ${plugin.name}: ${error41}`, { level: "error" });
284524
+ }
284525
+ }
284526
+ }
284527
+ }
284528
+ return pluginCommands;
284529
+ }));
284530
+ const allCommands = perPluginCommands.flat();
284531
+ logForDebugging2(`Total plugin commands loaded: ${allCommands.length}`);
284532
+ return allCommands;
284533
+ }
284161
284534
  function clearPluginCommandCache() {
284162
284535
  getPluginCommands.cache?.clear?.();
284163
284536
  }
284164
- async function loadSkillsFromDirectory(skillsPath, pluginName, sourceName, pluginManifest, pluginPath, loadedPaths) {
284537
+ async function loadSkillsFromDirectory(skillsPath, pluginName, sourceName, pluginManifest, pluginPath, loadedPaths, pluginDataPath, strict = false) {
284165
284538
  const fs2 = getFsImplementation();
284166
284539
  const skills = [];
284167
284540
  const directSkillPath = join62(skillsPath, "SKILL.md");
@@ -284172,6 +284545,8 @@ async function loadSkillsFromDirectory(skillsPath, pluginName, sourceName, plugi
284172
284545
  });
284173
284546
  } catch (e) {
284174
284547
  if (!isENOENT(e)) {
284548
+ if (strict)
284549
+ throw e;
284175
284550
  logForDebugging2(`Failed to load skill from ${directSkillPath}: ${e}`, {
284176
284551
  level: "error"
284177
284552
  });
@@ -284191,11 +284566,13 @@ async function loadSkillsFromDirectory(skillsPath, pluginName, sourceName, plugi
284191
284566
  frontmatter,
284192
284567
  content: markdownContent
284193
284568
  };
284194
- const skill = createPluginCommand(skillName, file2, sourceName, pluginManifest, pluginPath, true, { isSkillMode: true });
284569
+ const skill = createPluginCommand(skillName, file2, sourceName, pluginManifest, pluginPath, true, { isSkillMode: true }, pluginDataPath, strict);
284195
284570
  if (skill) {
284196
284571
  skills.push(skill);
284197
284572
  }
284198
284573
  } catch (error41) {
284574
+ if (strict)
284575
+ throw error41;
284199
284576
  logForDebugging2(`Failed to load skill from ${directSkillPath}: ${error41}`, {
284200
284577
  level: "error"
284201
284578
  });
@@ -284207,6 +284584,8 @@ async function loadSkillsFromDirectory(skillsPath, pluginName, sourceName, plugi
284207
284584
  entries = await fs2.readdir(skillsPath);
284208
284585
  } catch (e) {
284209
284586
  if (!isENOENT(e)) {
284587
+ if (strict)
284588
+ throw e;
284210
284589
  logForDebugging2(`Failed to load skills from directory ${skillsPath}: ${e}`, { level: "error" });
284211
284590
  }
284212
284591
  return skills;
@@ -284222,6 +284601,8 @@ async function loadSkillsFromDirectory(skillsPath, pluginName, sourceName, plugi
284222
284601
  content = await fs2.readFile(skillFilePath, { encoding: "utf-8" });
284223
284602
  } catch (e) {
284224
284603
  if (!isENOENT(e)) {
284604
+ if (strict)
284605
+ throw e;
284225
284606
  logForDebugging2(`Failed to load skill from ${skillFilePath}: ${e}`, {
284226
284607
  level: "error"
284227
284608
  });
@@ -284240,16 +284621,61 @@ async function loadSkillsFromDirectory(skillsPath, pluginName, sourceName, plugi
284240
284621
  frontmatter,
284241
284622
  content: markdownContent
284242
284623
  };
284243
- const skill = createPluginCommand(skillName, file2, sourceName, pluginManifest, pluginPath, true, { isSkillMode: true });
284624
+ const skill = createPluginCommand(skillName, file2, sourceName, pluginManifest, pluginPath, true, { isSkillMode: true }, pluginDataPath, strict);
284244
284625
  if (skill) {
284245
284626
  skills.push(skill);
284246
284627
  }
284247
284628
  } catch (error41) {
284629
+ if (strict)
284630
+ throw error41;
284248
284631
  logForDebugging2(`Failed to load skill from ${skillFilePath}: ${error41}`, { level: "error" });
284249
284632
  }
284250
284633
  }));
284251
284634
  return skills;
284252
284635
  }
284636
+ async function loadPluginSkillsFromPlugins(enabled, options2 = {}) {
284637
+ const strict = options2.strict ?? false;
284638
+ const perPluginSkills = await Promise.all(enabled.map(async (plugin) => {
284639
+ const loadedPaths = new Set;
284640
+ const pluginSkills = [];
284641
+ logForDebugging2(`Checking plugin ${plugin.name}: skillsPath=${plugin.skillsPath ? "exists" : "none"}, skillsPaths=${plugin.skillsPaths ? plugin.skillsPaths.length : 0} paths`);
284642
+ if (plugin.skillsPath) {
284643
+ logForDebugging2(`Attempting to load skills from plugin ${plugin.name} default skillsPath: ${plugin.skillsPath}`);
284644
+ try {
284645
+ const skills = await loadSkillsFromDirectory(plugin.skillsPath, plugin.name, plugin.source, plugin.manifest, plugin.path, loadedPaths, plugin.dataPath, strict);
284646
+ pluginSkills.push(...skills);
284647
+ logForDebugging2(`Loaded ${skills.length} skills from plugin ${plugin.name} default directory`);
284648
+ } catch (error41) {
284649
+ if (strict)
284650
+ throw error41;
284651
+ logForDebugging2(`Failed to load skills from plugin ${plugin.name} default directory: ${error41}`, { level: "error" });
284652
+ }
284653
+ }
284654
+ if (plugin.skillsPaths) {
284655
+ logForDebugging2(`Attempting to load skills from plugin ${plugin.name} skillsPaths: ${plugin.skillsPaths.join(", ")}`);
284656
+ const pathResults = await Promise.all(plugin.skillsPaths.map(async (skillPath) => {
284657
+ try {
284658
+ logForDebugging2(`Loading from skillPath: ${skillPath} for plugin ${plugin.name}`);
284659
+ const skills = await loadSkillsFromDirectory(skillPath, plugin.name, plugin.source, plugin.manifest, plugin.path, loadedPaths, plugin.dataPath, strict);
284660
+ logForDebugging2(`Loaded ${skills.length} skills from plugin ${plugin.name} custom path: ${skillPath}`);
284661
+ return skills;
284662
+ } catch (error41) {
284663
+ if (strict)
284664
+ throw error41;
284665
+ logForDebugging2(`Failed to load skills from plugin ${plugin.name} custom path ${skillPath}: ${error41}`, { level: "error" });
284666
+ return [];
284667
+ }
284668
+ }));
284669
+ for (const skills of pathResults) {
284670
+ pluginSkills.push(...skills);
284671
+ }
284672
+ }
284673
+ return pluginSkills;
284674
+ }));
284675
+ const allSkills = perPluginSkills.flat();
284676
+ logForDebugging2(`Total plugin skills loaded: ${allSkills.length}`);
284677
+ return allSkills;
284678
+ }
284253
284679
  function clearPluginSkillsCache() {
284254
284680
  getPluginSkills.cache?.clear?.();
284255
284681
  }
@@ -284278,140 +284704,7 @@ var init_loadPluginCommands = __esm(() => {
284278
284704
  if (errors4.length > 0) {
284279
284705
  logForDebugging2(`Plugin loading errors: ${errors4.map((e) => getPluginErrorMessage(e)).join(", ")}`);
284280
284706
  }
284281
- const perPluginCommands = await Promise.all(enabled.map(async (plugin) => {
284282
- const loadedPaths = new Set;
284283
- const pluginCommands = [];
284284
- if (plugin.commandsPath) {
284285
- try {
284286
- const commands = await loadCommandsFromDirectory(plugin.commandsPath, plugin.name, plugin.source, plugin.manifest, plugin.path, { isSkillMode: false }, loadedPaths);
284287
- pluginCommands.push(...commands);
284288
- if (commands.length > 0) {
284289
- logForDebugging2(`Loaded ${commands.length} commands from plugin ${plugin.name} default directory`);
284290
- }
284291
- } catch (error41) {
284292
- logForDebugging2(`Failed to load commands from plugin ${plugin.name} default directory: ${error41}`, { level: "error" });
284293
- }
284294
- }
284295
- if (plugin.commandsPaths) {
284296
- logForDebugging2(`Plugin ${plugin.name} has commandsPaths: ${plugin.commandsPaths.join(", ")}`);
284297
- const pathResults = await Promise.all(plugin.commandsPaths.map(async (commandPath) => {
284298
- try {
284299
- const fs2 = getFsImplementation();
284300
- const stats = await fs2.stat(commandPath);
284301
- logForDebugging2(`Checking commandPath ${commandPath} - isDirectory: ${stats.isDirectory()}, isFile: ${stats.isFile()}`);
284302
- if (stats.isDirectory()) {
284303
- const commands = await loadCommandsFromDirectory(commandPath, plugin.name, plugin.source, plugin.manifest, plugin.path, { isSkillMode: false }, loadedPaths);
284304
- if (commands.length > 0) {
284305
- logForDebugging2(`Loaded ${commands.length} commands from plugin ${plugin.name} custom path: ${commandPath}`);
284306
- } else {
284307
- logForDebugging2(`Warning: No commands found in plugin ${plugin.name} custom directory: ${commandPath}. Expected .md files or SKILL.md in subdirectories.`, { level: "warn" });
284308
- }
284309
- return commands;
284310
- } else if (stats.isFile() && commandPath.endsWith(".md")) {
284311
- if (isDuplicatePath(fs2, commandPath, loadedPaths)) {
284312
- return [];
284313
- }
284314
- const content = await fs2.readFile(commandPath, {
284315
- encoding: "utf-8"
284316
- });
284317
- const { frontmatter, content: markdownContent } = parseFrontmatter(content, commandPath);
284318
- let commandName;
284319
- let metadataOverride;
284320
- if (plugin.commandsMetadata) {
284321
- for (const [name, metadata] of Object.entries(plugin.commandsMetadata)) {
284322
- if (metadata.source) {
284323
- const fullMetadataPath = join62(plugin.path, metadata.source);
284324
- if (commandPath === fullMetadataPath) {
284325
- commandName = `${plugin.name}:${name}`;
284326
- metadataOverride = metadata;
284327
- break;
284328
- }
284329
- }
284330
- }
284331
- }
284332
- if (!commandName) {
284333
- commandName = `${plugin.name}:${basename16(commandPath).replace(/\.md$/, "")}`;
284334
- }
284335
- const finalFrontmatter = metadataOverride ? {
284336
- ...frontmatter,
284337
- ...metadataOverride.description && {
284338
- description: metadataOverride.description
284339
- },
284340
- ...metadataOverride.argumentHint && {
284341
- "argument-hint": metadataOverride.argumentHint
284342
- },
284343
- ...metadataOverride.model && {
284344
- model: metadataOverride.model
284345
- },
284346
- ...metadataOverride.allowedTools && {
284347
- "allowed-tools": metadataOverride.allowedTools.join(",")
284348
- }
284349
- } : frontmatter;
284350
- const file2 = {
284351
- filePath: commandPath,
284352
- baseDir: dirname29(commandPath),
284353
- frontmatter: finalFrontmatter,
284354
- content: markdownContent
284355
- };
284356
- const command = createPluginCommand(commandName, file2, plugin.source, plugin.manifest, plugin.path, false);
284357
- if (command) {
284358
- logForDebugging2(`Loaded command from plugin ${plugin.name} custom file: ${commandPath}${metadataOverride ? " (with metadata override)" : ""}`);
284359
- return [command];
284360
- }
284361
- }
284362
- return [];
284363
- } catch (error41) {
284364
- logForDebugging2(`Failed to load commands from plugin ${plugin.name} custom path ${commandPath}: ${error41}`, { level: "error" });
284365
- return [];
284366
- }
284367
- }));
284368
- for (const commands of pathResults) {
284369
- pluginCommands.push(...commands);
284370
- }
284371
- }
284372
- if (plugin.commandsMetadata) {
284373
- for (const [name, metadata] of Object.entries(plugin.commandsMetadata)) {
284374
- if (metadata.content && !metadata.source) {
284375
- try {
284376
- const { frontmatter, content: markdownContent } = parseFrontmatter(metadata.content, `<inline:${plugin.name}:${name}>`);
284377
- const finalFrontmatter = {
284378
- ...frontmatter,
284379
- ...metadata.description && {
284380
- description: metadata.description
284381
- },
284382
- ...metadata.argumentHint && {
284383
- "argument-hint": metadata.argumentHint
284384
- },
284385
- ...metadata.model && {
284386
- model: metadata.model
284387
- },
284388
- ...metadata.allowedTools && {
284389
- "allowed-tools": metadata.allowedTools.join(",")
284390
- }
284391
- };
284392
- const commandName = `${plugin.name}:${name}`;
284393
- const file2 = {
284394
- filePath: `<inline:${commandName}>`,
284395
- baseDir: plugin.path,
284396
- frontmatter: finalFrontmatter,
284397
- content: markdownContent
284398
- };
284399
- const command = createPluginCommand(commandName, file2, plugin.source, plugin.manifest, plugin.path, false);
284400
- if (command) {
284401
- pluginCommands.push(command);
284402
- logForDebugging2(`Loaded inline content command from plugin ${plugin.name}: ${commandName}`);
284403
- }
284404
- } catch (error41) {
284405
- logForDebugging2(`Failed to load inline content command ${name} from plugin ${plugin.name}: ${error41}`, { level: "error" });
284406
- }
284407
- }
284408
- }
284409
- }
284410
- return pluginCommands;
284411
- }));
284412
- const allCommands = perPluginCommands.flat();
284413
- logForDebugging2(`Total plugin commands loaded: ${allCommands.length}`);
284414
- return allCommands;
284707
+ return loadPluginCommandsFromPlugins(enabled);
284415
284708
  });
284416
284709
  getPluginSkills = memoize_default(async () => {
284417
284710
  if (isBareMode() && getInlinePlugins().length === 0) {
@@ -284422,48 +284715,14 @@ var init_loadPluginCommands = __esm(() => {
284422
284715
  logForDebugging2(`Plugin loading errors: ${errors4.map((e) => getPluginErrorMessage(e)).join(", ")}`);
284423
284716
  }
284424
284717
  logForDebugging2(`getPluginSkills: Processing ${enabled.length} enabled plugins`);
284425
- const perPluginSkills = await Promise.all(enabled.map(async (plugin) => {
284426
- const loadedPaths = new Set;
284427
- const pluginSkills = [];
284428
- logForDebugging2(`Checking plugin ${plugin.name}: skillsPath=${plugin.skillsPath ? "exists" : "none"}, skillsPaths=${plugin.skillsPaths ? plugin.skillsPaths.length : 0} paths`);
284429
- if (plugin.skillsPath) {
284430
- logForDebugging2(`Attempting to load skills from plugin ${plugin.name} default skillsPath: ${plugin.skillsPath}`);
284431
- try {
284432
- const skills = await loadSkillsFromDirectory(plugin.skillsPath, plugin.name, plugin.source, plugin.manifest, plugin.path, loadedPaths);
284433
- pluginSkills.push(...skills);
284434
- logForDebugging2(`Loaded ${skills.length} skills from plugin ${plugin.name} default directory`);
284435
- } catch (error41) {
284436
- logForDebugging2(`Failed to load skills from plugin ${plugin.name} default directory: ${error41}`, { level: "error" });
284437
- }
284438
- }
284439
- if (plugin.skillsPaths) {
284440
- logForDebugging2(`Attempting to load skills from plugin ${plugin.name} skillsPaths: ${plugin.skillsPaths.join(", ")}`);
284441
- const pathResults = await Promise.all(plugin.skillsPaths.map(async (skillPath) => {
284442
- try {
284443
- logForDebugging2(`Loading from skillPath: ${skillPath} for plugin ${plugin.name}`);
284444
- const skills = await loadSkillsFromDirectory(skillPath, plugin.name, plugin.source, plugin.manifest, plugin.path, loadedPaths);
284445
- logForDebugging2(`Loaded ${skills.length} skills from plugin ${plugin.name} custom path: ${skillPath}`);
284446
- return skills;
284447
- } catch (error41) {
284448
- logForDebugging2(`Failed to load skills from plugin ${plugin.name} custom path ${skillPath}: ${error41}`, { level: "error" });
284449
- return [];
284450
- }
284451
- }));
284452
- for (const skills of pathResults) {
284453
- pluginSkills.push(...skills);
284454
- }
284455
- }
284456
- return pluginSkills;
284457
- }));
284458
- const allSkills = perPluginSkills.flat();
284459
- logForDebugging2(`Total plugin skills loaded: ${allSkills.length}`);
284460
- return allSkills;
284718
+ return loadPluginSkillsFromPlugins(enabled);
284461
284719
  });
284462
284720
  });
284463
284721
 
284464
284722
  // src/capabilities/plugins/loadPluginHooks.ts
284465
284723
  var exports_loadPluginHooks = {};
284466
284724
  __export(exports_loadPluginHooks, {
284725
+ buildExplicitPluginHookMatchers: () => buildExplicitPluginHookMatchers,
284467
284726
  clearPluginHookCache: () => clearPluginHookCache,
284468
284727
  getPluginAffectingSettingsSnapshot: () => getPluginAffectingSettingsSnapshot,
284469
284728
  loadPluginHooks: () => loadPluginHooks,
@@ -284471,6 +284730,33 @@ __export(exports_loadPluginHooks, {
284471
284730
  resetHotReloadState: () => resetHotReloadState,
284472
284731
  setupPluginHookHotReload: () => setupPluginHookHotReload
284473
284732
  });
284733
+ function buildExplicitPluginHookMatchers(plugins) {
284734
+ const result = {};
284735
+ for (const event of PLUGIN_HOOK_EVENTS)
284736
+ result[event] = [];
284737
+ for (const plugin of plugins) {
284738
+ if (!plugin.hooksConfig)
284739
+ continue;
284740
+ for (const [event, matchers] of Object.entries(plugin.hooksConfig)) {
284741
+ if (!PLUGIN_HOOK_EVENTS.includes(event))
284742
+ continue;
284743
+ const hookEvent = event;
284744
+ const target = result[hookEvent];
284745
+ for (const matcher of matchers ?? []) {
284746
+ if (matcher.hooks.length === 0)
284747
+ continue;
284748
+ target.push({
284749
+ matcher: matcher.matcher,
284750
+ hooks: matcher.hooks,
284751
+ pluginRoot: plugin.path,
284752
+ pluginName: plugin.name,
284753
+ pluginId: plugin.source
284754
+ });
284755
+ }
284756
+ }
284757
+ }
284758
+ return result;
284759
+ }
284474
284760
  function convertPluginHooksToMatchers(plugin) {
284475
284761
  const pluginMatchers = {
284476
284762
  PreToolUse: [],
@@ -284579,7 +284865,7 @@ function setupPluginHookHotReload() {
284579
284865
  }
284580
284866
  });
284581
284867
  }
284582
- var hotReloadSubscribed = false, lastPluginSettingsSnapshot, loadPluginHooks;
284868
+ var hotReloadSubscribed = false, lastPluginSettingsSnapshot, PLUGIN_HOOK_EVENTS, loadPluginHooks;
284583
284869
  var init_loadPluginHooks = __esm(() => {
284584
284870
  init_memoize();
284585
284871
  init_state2();
@@ -284588,6 +284874,35 @@ var init_loadPluginHooks = __esm(() => {
284588
284874
  init_settings2();
284589
284875
  init_slowOperations();
284590
284876
  init_pluginLoader();
284877
+ PLUGIN_HOOK_EVENTS = [
284878
+ "PreToolUse",
284879
+ "PostToolUse",
284880
+ "PostToolUseFailure",
284881
+ "PermissionDenied",
284882
+ "Notification",
284883
+ "UserPromptSubmit",
284884
+ "SessionStart",
284885
+ "SessionEnd",
284886
+ "Stop",
284887
+ "StopFailure",
284888
+ "SubagentStart",
284889
+ "SubagentStop",
284890
+ "PreCompact",
284891
+ "PostCompact",
284892
+ "PermissionRequest",
284893
+ "Setup",
284894
+ "TeammateIdle",
284895
+ "TaskCreated",
284896
+ "TaskCompleted",
284897
+ "Elicitation",
284898
+ "ElicitationResult",
284899
+ "ConfigChange",
284900
+ "WorktreeCreate",
284901
+ "WorktreeRemove",
284902
+ "InstructionsLoaded",
284903
+ "CwdChanged",
284904
+ "FileChanged"
284905
+ ];
284591
284906
  loadPluginHooks = memoize_default(async () => {
284592
284907
  const { enabled } = await loadAllPluginsCacheOnly();
284593
284908
  const allPluginHooks = {
@@ -284638,16 +284953,16 @@ var init_loadPluginHooks = __esm(() => {
284638
284953
 
284639
284954
  // src/capabilities/plugins/loadPluginOutputStyles.ts
284640
284955
  import { basename as basename17 } from "path";
284641
- async function loadOutputStylesFromDirectory(outputStylesPath, pluginName, loadedPaths) {
284956
+ async function loadOutputStylesFromDirectory(outputStylesPath, pluginName, sourceName, loadedPaths, strict = false) {
284642
284957
  const styles4 = [];
284643
284958
  await walkPluginMarkdown(outputStylesPath, async (fullPath) => {
284644
- const style = await loadOutputStyleFromFile(fullPath, pluginName, loadedPaths);
284959
+ const style = await loadOutputStyleFromFile(fullPath, pluginName, sourceName, loadedPaths, strict);
284645
284960
  if (style)
284646
284961
  styles4.push(style);
284647
284962
  }, { logLabel: "output-styles" });
284648
284963
  return styles4;
284649
284964
  }
284650
- async function loadOutputStyleFromFile(filePath, pluginName, loadedPaths) {
284965
+ async function loadOutputStyleFromFile(filePath, pluginName, sourceName, loadedPaths, strict = false) {
284651
284966
  const fs2 = getFsImplementation();
284652
284967
  if (isDuplicatePath(fs2, filePath, loadedPaths)) {
284653
284968
  return null;
@@ -284666,15 +284981,65 @@ async function loadOutputStyleFromFile(filePath, pluginName, loadedPaths) {
284666
284981
  description,
284667
284982
  prompt: markdownContent.trim(),
284668
284983
  source: "plugin",
284984
+ plugin: sourceName,
284669
284985
  forceForPlugin
284670
284986
  };
284671
284987
  } catch (error41) {
284988
+ if (strict)
284989
+ throw error41;
284672
284990
  logForDebugging2(`Failed to load output style from ${filePath}: ${error41}`, {
284673
284991
  level: "error"
284674
284992
  });
284675
284993
  return null;
284676
284994
  }
284677
284995
  }
284996
+ async function loadPluginOutputStylesFromPlugins(enabled, options2 = {}) {
284997
+ const strict = options2.strict ?? false;
284998
+ const allStyles = [];
284999
+ for (const plugin of enabled) {
285000
+ const loadedPaths = new Set;
285001
+ if (plugin.outputStylesPath) {
285002
+ try {
285003
+ const styles4 = await loadOutputStylesFromDirectory(plugin.outputStylesPath, plugin.name, plugin.source, loadedPaths, strict);
285004
+ allStyles.push(...styles4);
285005
+ if (styles4.length > 0) {
285006
+ logForDebugging2(`Loaded ${styles4.length} output styles from plugin ${plugin.name} default directory`);
285007
+ }
285008
+ } catch (error41) {
285009
+ if (strict)
285010
+ throw error41;
285011
+ logForDebugging2(`Failed to load output styles from plugin ${plugin.name} default directory: ${error41}`, { level: "error" });
285012
+ }
285013
+ }
285014
+ if (plugin.outputStylesPaths) {
285015
+ for (const stylePath of plugin.outputStylesPaths) {
285016
+ try {
285017
+ const fs2 = getFsImplementation();
285018
+ const stats = await fs2.stat(stylePath);
285019
+ if (stats.isDirectory()) {
285020
+ const styles4 = await loadOutputStylesFromDirectory(stylePath, plugin.name, plugin.source, loadedPaths, strict);
285021
+ allStyles.push(...styles4);
285022
+ if (styles4.length > 0) {
285023
+ logForDebugging2(`Loaded ${styles4.length} output styles from plugin ${plugin.name} custom path: ${stylePath}`);
285024
+ }
285025
+ } else if (stats.isFile() && stylePath.endsWith(".md")) {
285026
+ const style = await loadOutputStyleFromFile(stylePath, plugin.name, plugin.source, loadedPaths, strict);
285027
+ if (style) {
285028
+ allStyles.push(style);
285029
+ logForDebugging2(`Loaded output style from plugin ${plugin.name} custom file: ${stylePath}`);
285030
+ }
285031
+ }
285032
+ } catch (error41) {
285033
+ if (strict)
285034
+ throw error41;
285035
+ logForDebugging2(`Failed to load output styles from plugin ${plugin.name} custom path ${stylePath}: ${error41}`, { level: "error" });
285036
+ }
285037
+ }
285038
+ }
285039
+ }
285040
+ logForDebugging2(`Total plugin output styles loaded: ${allStyles.length}`);
285041
+ return allStyles;
285042
+ }
284678
285043
  function clearPluginOutputStyleCache() {
284679
285044
  loadPluginOutputStyles.cache?.clear?.();
284680
285045
  }
@@ -284689,49 +285054,10 @@ var init_loadPluginOutputStyles = __esm(() => {
284689
285054
  init_walkPluginMarkdown();
284690
285055
  loadPluginOutputStyles = memoize_default(async () => {
284691
285056
  const { enabled, errors: errors4 } = await loadAllPluginsCacheOnly();
284692
- const allStyles = [];
284693
285057
  if (errors4.length > 0) {
284694
285058
  logForDebugging2(`Plugin loading errors: ${errors4.map((e) => getPluginErrorMessage(e)).join(", ")}`);
284695
285059
  }
284696
- for (const plugin of enabled) {
284697
- const loadedPaths = new Set;
284698
- if (plugin.outputStylesPath) {
284699
- try {
284700
- const styles4 = await loadOutputStylesFromDirectory(plugin.outputStylesPath, plugin.name, loadedPaths);
284701
- allStyles.push(...styles4);
284702
- if (styles4.length > 0) {
284703
- logForDebugging2(`Loaded ${styles4.length} output styles from plugin ${plugin.name} default directory`);
284704
- }
284705
- } catch (error41) {
284706
- logForDebugging2(`Failed to load output styles from plugin ${plugin.name} default directory: ${error41}`, { level: "error" });
284707
- }
284708
- }
284709
- if (plugin.outputStylesPaths) {
284710
- for (const stylePath of plugin.outputStylesPaths) {
284711
- try {
284712
- const fs2 = getFsImplementation();
284713
- const stats = await fs2.stat(stylePath);
284714
- if (stats.isDirectory()) {
284715
- const styles4 = await loadOutputStylesFromDirectory(stylePath, plugin.name, loadedPaths);
284716
- allStyles.push(...styles4);
284717
- if (styles4.length > 0) {
284718
- logForDebugging2(`Loaded ${styles4.length} output styles from plugin ${plugin.name} custom path: ${stylePath}`);
284719
- }
284720
- } else if (stats.isFile() && stylePath.endsWith(".md")) {
284721
- const style = await loadOutputStyleFromFile(stylePath, plugin.name, loadedPaths);
284722
- if (style) {
284723
- allStyles.push(style);
284724
- logForDebugging2(`Loaded output style from plugin ${plugin.name} custom file: ${stylePath}`);
284725
- }
284726
- }
284727
- } catch (error41) {
284728
- logForDebugging2(`Failed to load output styles from plugin ${plugin.name} custom path ${stylePath}: ${error41}`, { level: "error" });
284729
- }
284730
- }
284731
- }
284732
- }
284733
- logForDebugging2(`Total plugin output styles loaded: ${allStyles.length}`);
284734
- return allStyles;
285060
+ return loadPluginOutputStylesFromPlugins(enabled);
284735
285061
  });
284736
285062
  });
284737
285063
 
@@ -287606,7 +287932,7 @@ var init_pluginInstallationHelpers = __esm(() => {
287606
287932
  });
287607
287933
 
287608
287934
  // src/capabilities/plugins/pluginLoader.ts
287609
- import { basename as basename20, dirname as dirname35, join as join69, relative as relative11, resolve as resolve29, sep as sep20 } from "path";
287935
+ import { basename as basename20, dirname as dirname35, isAbsolute as isAbsolute21, join as join69, relative as relative11, resolve as resolve29, sep as sep20 } from "path";
287610
287936
  function getPluginCachePath() {
287611
287937
  return join69(getPluginsDirectory(), "cache");
287612
287938
  }
@@ -288103,14 +288429,31 @@ async function loadPluginHooks2(hooksConfigPath, pluginName) {
288103
288429
  return validatedPluginHooks.hooks;
288104
288430
  }
288105
288431
  async function validatePluginPaths(relPaths, pluginPath, pluginName, source, component, componentLabel, contextLabel, errors4) {
288432
+ const fs2 = getFsImplementation();
288433
+ const pluginRoot = await fs2.realpath(pluginPath);
288106
288434
  const checks4 = await Promise.all(relPaths.map(async (relPath) => {
288107
- const fullPath = join69(pluginPath, relPath);
288108
- return { relPath, fullPath, exists: await pathExists(fullPath) };
288435
+ const fullPath = resolve29(pluginPath, relPath);
288436
+ if (!await pathExists(fullPath)) {
288437
+ return { relPath, fullPath, exists: false, escaped: false };
288438
+ }
288439
+ const realPath = await fs2.realpath(fullPath);
288440
+ const pathFromRoot = relative11(pluginRoot, realPath);
288441
+ const escaped = pathFromRoot === ".." || pathFromRoot.startsWith(`..${sep20}`) || isAbsolute21(pathFromRoot);
288442
+ return { relPath, fullPath, exists: true, escaped };
288109
288443
  }));
288110
288444
  const validPaths = [];
288111
- for (const { relPath, fullPath, exists } of checks4) {
288112
- if (exists) {
288445
+ for (const { relPath, fullPath, exists, escaped } of checks4) {
288446
+ if (exists && !escaped) {
288113
288447
  validPaths.push(fullPath);
288448
+ } else if (escaped) {
288449
+ errors4.push({
288450
+ type: "component-load-failed",
288451
+ source,
288452
+ plugin: pluginName,
288453
+ path: fullPath,
288454
+ component,
288455
+ reason: "Path resolves outside the plugin root"
288456
+ });
288114
288457
  } else {
288115
288458
  logForDebugging2(`${componentLabel} path ${relPath} ${contextLabel} not found at ${fullPath} for ${pluginName}`, { level: "warn" });
288116
288459
  logError2(new Error(`Plugin component file not found: ${fullPath} for ${pluginName}`));
@@ -305546,7 +305889,7 @@ var builders = null;
305546
305889
  import {
305547
305890
  basename as basename22,
305548
305891
  dirname as dirname39,
305549
- isAbsolute as isAbsolute21,
305892
+ isAbsolute as isAbsolute22,
305550
305893
  join as join78,
305551
305894
  sep as pathSep2,
305552
305895
  relative as relative13
@@ -306029,8 +306372,8 @@ function activateConditionalSkillsForPaths(filePaths, cwd) {
306029
306372
  }
306030
306373
  const skillIgnore = import_ignore2.default().add(skill.paths);
306031
306374
  for (const filePath of filePaths) {
306032
- const relativePath = isAbsolute21(filePath) ? relative13(cwd, filePath) : filePath;
306033
- if (!relativePath || relativePath.startsWith("..") || isAbsolute21(relativePath)) {
306375
+ const relativePath = isAbsolute22(filePath) ? relative13(cwd, filePath) : filePath;
306376
+ if (!relativePath || relativePath.startsWith("..") || isAbsolute22(relativePath)) {
306034
306377
  continue;
306035
306378
  }
306036
306379
  if (skillIgnore.ignores(relativePath)) {
@@ -342619,14 +342962,14 @@ var init_measure_text = __esm(() => {
342619
342962
  });
342620
342963
 
342621
342964
  // src/cli/ink/node-cache.ts
342622
- function addPendingClear(parent, rect, isAbsolute22) {
342965
+ function addPendingClear(parent, rect, isAbsolute23) {
342623
342966
  const existing = pendingClears.get(parent);
342624
342967
  if (existing) {
342625
342968
  existing.push(rect);
342626
342969
  } else {
342627
342970
  pendingClears.set(parent, [rect]);
342628
342971
  }
342629
- if (isAbsolute22) {
342972
+ if (isAbsolute23) {
342630
342973
  absoluteNodeRemoved = true;
342631
342974
  }
342632
342975
  }
@@ -343008,17 +343351,17 @@ function collectRemovedRects(parent, removed, underAbsolute = false) {
343008
343351
  if (!removed || removed.nodeName === "#text")
343009
343352
  return;
343010
343353
  const elem = removed;
343011
- const isAbsolute22 = underAbsolute || elem.style?.position === "absolute";
343354
+ const isAbsolute23 = underAbsolute || elem.style?.position === "absolute";
343012
343355
  const cached3 = nodeCache.get(elem);
343013
343356
  if (cached3) {
343014
- addPendingClear(parent, cached3, isAbsolute22);
343357
+ addPendingClear(parent, cached3, isAbsolute23);
343015
343358
  nodeCache.delete(elem);
343016
343359
  }
343017
343360
  const childNodes = Array.isArray(elem.childNodes) ? [...elem.childNodes] : [];
343018
343361
  for (const child of childNodes) {
343019
343362
  if (!child)
343020
343363
  continue;
343021
- collectRemovedRects(parent, child, isAbsolute22);
343364
+ collectRemovedRects(parent, child, isAbsolute23);
343022
343365
  }
343023
343366
  }
343024
343367
  function stylesEqual(a2, b) {
@@ -349480,16 +349823,16 @@ function renderChildren(node, output, offsetX, offsetY, hasRemovedChild, prevScr
349480
349823
  }
349481
349824
  const childElem = childNode;
349482
349825
  const wasDirty = childElem.dirty;
349483
- const isAbsolute22 = childElem.style.position === "absolute";
349826
+ const isAbsolute23 = childElem.style.position === "absolute";
349484
349827
  renderNodeToOutput(childElem, output, {
349485
349828
  offsetX,
349486
349829
  offsetY,
349487
349830
  prevScreen: hasRemovedChild || seenDirtyChild ? undefined : prevScreen,
349488
- skipSelfBlit: seenDirtyClipped && isAbsolute22 && !childElem.style.opaque && childElem.style.backgroundColor === undefined,
349831
+ skipSelfBlit: seenDirtyClipped && isAbsolute23 && !childElem.style.opaque && childElem.style.backgroundColor === undefined,
349489
349832
  inheritedBackgroundColor
349490
349833
  });
349491
349834
  if (wasDirty && !seenDirtyChild) {
349492
- if (!clipsBothAxes(childElem) || isAbsolute22) {
349835
+ if (!clipsBothAxes(childElem) || isAbsolute23) {
349493
349836
  seenDirtyChild = true;
349494
349837
  } else {
349495
349838
  seenDirtyClipped = true;
@@ -353657,7 +354000,7 @@ var init_ink3 = __esm(() => {
353657
354000
 
353658
354001
  // src/capabilities/imagePaste.ts
353659
354002
  import { randomBytes as randomBytes12 } from "crypto";
353660
- import { basename as basename27, extname as extname8, isAbsolute as isAbsolute22, join as join85 } from "path";
354003
+ import { basename as basename27, extname as extname8, isAbsolute as isAbsolute23, join as join85 } from "path";
353661
354004
  function buildLinuxClipboardCheckCommand() {
353662
354005
  const mimePattern = LINUX_CLIPBOARD_IMAGE_MIME_TYPES.map((mimeType) => mimeType.replace("/", "\\/")).join("|");
353663
354006
  return `xclip -selection clipboard -t TARGETS -o 2>/dev/null | grep -E "${mimePattern}" || wl-paste -l 2>/dev/null | grep -E "${mimePattern}"`;
@@ -353804,7 +354147,7 @@ async function tryReadImageFromPath(text) {
353804
354147
  const imagePath = cleanedPath;
353805
354148
  let imageBuffer;
353806
354149
  try {
353807
- if (isAbsolute22(imagePath)) {
354150
+ if (isAbsolute23(imagePath)) {
353808
354151
  imageBuffer = getFsImplementation().readFileBytesSync(imagePath);
353809
354152
  } else {
353810
354153
  const clipboardPath = await getImagePathFromClipboard();
@@ -482433,7 +482776,7 @@ var init_usePluginAutoupdateNotification = __esm(() => {
482433
482776
  });
482434
482777
 
482435
482778
  // src/capabilities/plugins/reconciler.ts
482436
- import { isAbsolute as isAbsolute23, resolve as resolve37 } from "path";
482779
+ import { isAbsolute as isAbsolute24, resolve as resolve37 } from "path";
482437
482780
  function diffMarketplaces(declared, materialized, opts) {
482438
482781
  const missing = [];
482439
482782
  const sourceChanged = [];
@@ -482541,7 +482884,7 @@ async function reconcileMarketplaces(opts) {
482541
482884
  return { installed, updated, failed, upToDate: diff2.upToDate, skipped };
482542
482885
  }
482543
482886
  function normalizeSource(source, projectRoot) {
482544
- if ((source.source === "directory" || source.source === "file") && !isAbsolute23(source.path)) {
482887
+ if ((source.source === "directory" || source.source === "file") && !isAbsolute24(source.path)) {
482545
482888
  const base2 = projectRoot ?? getOriginalCwd();
482546
482889
  const canonicalRoot = findCanonicalGitRoot(base2);
482547
482890
  return {
@@ -492185,7 +492528,7 @@ function buildPrimarySection() {
492185
492528
  }, undefined, false, undefined, this);
492186
492529
  return [{
492187
492530
  label: "Version",
492188
- value: "0.4.22"
492531
+ value: "0.4.24"
492189
492532
  }, {
492190
492533
  label: "Session name",
492191
492534
  value: nameValue
@@ -540327,7 +540670,7 @@ var init_bridge_kick = __esm(() => {
540327
540670
  var call58 = async () => {
540328
540671
  return {
540329
540672
  type: "text",
540330
- value: `${"99.0.0"} (built ${"2026-08-21T04:07:58.719Z"})`
540673
+ value: `${"99.0.0"} (built ${"2026-09-03T09:12:13.936Z"})`
540331
540674
  };
540332
540675
  }, version2, version_default;
540333
540676
  var init_version = __esm(() => {
@@ -553010,7 +553353,7 @@ __export(exports_UI12, {
553010
553353
  renderToolUseRejectedMessage: () => renderToolUseRejectedMessage14,
553011
553354
  userFacingName: () => userFacingName11
553012
553355
  });
553013
- import { isAbsolute as isAbsolute24, relative as relative31, resolve as resolve41 } from "path";
553356
+ import { isAbsolute as isAbsolute25, relative as relative31, resolve as resolve41 } from "path";
553014
553357
  function countLines(content) {
553015
553358
  const parts = content.split(EOL5);
553016
553359
  return content.endsWith(EOL5) ? parts.length - 1 : parts.length;
@@ -553334,7 +553677,7 @@ function WriteRejectionBody(t0) {
553334
553677
  }
553335
553678
  async function loadRejectionDiff2(filePath, content) {
553336
553679
  try {
553337
- const fullFilePath = isAbsolute24(filePath) ? filePath : resolve41(getCwd2(), filePath);
553680
+ const fullFilePath = isAbsolute25(filePath) ? filePath : resolve41(getCwd2(), filePath);
553338
553681
  const handle = await openForScan(fullFilePath);
553339
553682
  if (handle === null)
553340
553683
  return {
@@ -558094,7 +558437,7 @@ function WelcomeV2() {
558094
558437
  dimColor: true,
558095
558438
  children: [
558096
558439
  "v",
558097
- "0.4.22",
558440
+ "0.4.24",
558098
558441
  " "
558099
558442
  ]
558100
558443
  }, undefined, true, undefined, this)
@@ -558294,7 +558637,7 @@ function WelcomeV2() {
558294
558637
  dimColor: true,
558295
558638
  children: [
558296
558639
  "v",
558297
- "0.4.22",
558640
+ "0.4.24",
558298
558641
  " "
558299
558642
  ]
558300
558643
  }, undefined, true, undefined, this)
@@ -558520,7 +558863,7 @@ function AppleTerminalWelcomeV2(t0) {
558520
558863
  dimColor: true,
558521
558864
  children: [
558522
558865
  "v",
558523
- "0.4.22",
558866
+ "0.4.24",
558524
558867
  " "
558525
558868
  ]
558526
558869
  }, undefined, true, undefined, this);
@@ -558774,7 +559117,7 @@ function AppleTerminalWelcomeV2(t0) {
558774
559117
  dimColor: true,
558775
559118
  children: [
558776
559119
  "v",
558777
- "0.4.22",
559120
+ "0.4.24",
558778
559121
  " "
558779
559122
  ]
558780
559123
  }, undefined, true, undefined, this);
@@ -569534,6 +569877,7 @@ class QueryEngine {
569534
569877
  includePartialMessages = false,
569535
569878
  agents: agents2 = [],
569536
569879
  setSDKStatus,
569880
+ preDecidePermissions,
569537
569881
  onToolInvoke,
569538
569882
  uploadMedia,
569539
569883
  orphanedPermission
@@ -569611,7 +569955,8 @@ class QueryEngine {
569611
569955
  maxOutputTokensLimit,
569612
569956
  contextWindow,
569613
569957
  modelProviders: this.config.modelProviders,
569614
- subagentDisallowedTools: this.config.subagentDisallowedTools
569958
+ subagentDisallowedTools: this.config.subagentDisallowedTools,
569959
+ preDecidePermissions
569615
569960
  },
569616
569961
  getAppState,
569617
569962
  setAppState,
@@ -569709,7 +570054,8 @@ class QueryEngine {
569709
570054
  maxOutputTokensLimit,
569710
570055
  contextWindow,
569711
570056
  modelProviders: this.config.modelProviders,
569712
- subagentDisallowedTools: this.config.subagentDisallowedTools
570057
+ subagentDisallowedTools: this.config.subagentDisallowedTools,
570058
+ preDecidePermissions
569713
570059
  },
569714
570060
  getAppState,
569715
570061
  setAppState,
@@ -570226,6 +570572,7 @@ async function* ask({
570226
570572
  handleElicitation,
570227
570573
  agents: agents2 = [],
570228
570574
  setSDKStatus,
570575
+ preDecidePermissions,
570229
570576
  onToolInvoke,
570230
570577
  uploadMedia,
570231
570578
  orphanedPermission
@@ -570260,6 +570607,7 @@ async function* ask({
570260
570607
  replayUserMessages,
570261
570608
  includePartialMessages,
570262
570609
  setSDKStatus,
570610
+ preDecidePermissions,
570263
570611
  onToolInvoke,
570264
570612
  uploadMedia,
570265
570613
  abortController,
@@ -579759,7 +580107,7 @@ Usage: claude --remote "your task description"`, () => gracefulShutdown(1));
579759
580107
  pendingHookMessages
579760
580108
  }, renderAndRun);
579761
580109
  }
579762
- }).version("0.4.22 (OpenCow)", "-v, --version", "Output the version number");
580110
+ }).version("0.4.24 (OpenCow)", "-v, --version", "Output the version number");
579763
580111
  program2.option("-w, --worktree [name]", "Create a new git worktree for this session (optionally specify a name)");
579764
580112
  program2.option("--tmux", "Create a tmux session for the worktree (requires --worktree). Uses iTerm2 native panes when available; use --tmux=classic for traditional tmux.");
579765
580113
  if (canUserConfigureAdvisor()) {
@@ -580404,7 +580752,7 @@ if (false) {}
580404
580752
  async function main2() {
580405
580753
  const args = process.argv.slice(2);
580406
580754
  if (args.length === 1 && (args[0] === "--version" || args[0] === "-v" || args[0] === "-V")) {
580407
- console.log(`${"0.4.22"} (OpenCow)`);
580755
+ console.log(`${"0.4.24"} (OpenCow)`);
580408
580756
  return;
580409
580757
  }
580410
580758
  if (args.includes("--provider")) {
@@ -580522,4 +580870,4 @@ async function main2() {
580522
580870
  }
580523
580871
  main2();
580524
580872
 
580525
- //# debugId=42468A73C022880964756E2164756E21
580873
+ //# debugId=686B073019ED8C6564756E2164756E21