juno-code 1.0.51 → 1.0.53

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.mjs CHANGED
@@ -1,5 +1,6 @@
1
1
  #!/usr/bin/env node
2
2
  import chalk from 'chalk';
3
+ import * as childProcess from 'child_process';
3
4
  import { spawn } from 'child_process';
4
5
  import * as fs3 from 'fs';
5
6
  import { promises } from 'fs';
@@ -11,6 +12,7 @@ import { z } from 'zod';
11
12
  import * as yaml from 'js-yaml';
12
13
  import { EventEmitter } from 'events';
13
14
  import { execa } from 'execa';
15
+ import { promisify } from 'util';
14
16
  import { v4 } from 'uuid';
15
17
  import * as process2 from 'process';
16
18
 
@@ -34,7 +36,7 @@ var __export = (target, all) => {
34
36
  var version;
35
37
  var init_version = __esm({
36
38
  "src/version.ts"() {
37
- version = "1.0.51";
39
+ version = "1.0.53";
38
40
  }
39
41
  });
40
42
 
@@ -722,25 +724,28 @@ var init_shell_backend = __esm({
722
724
  const scriptPath = await this.findScriptForSubagent(subagentType);
723
725
  const result = await this.executeScript(scriptPath, request, toolId, subagentType);
724
726
  const duration = Date.now() - startTime;
727
+ const structuredResult = this.buildStructuredOutput(subagentType, result);
728
+ const structuredPayload = this.parseStructuredResultPayload(structuredResult.content);
729
+ const structuredIndicatesError = structuredPayload?.is_error === true || structuredPayload?.subtype === "error";
730
+ const executionSucceeded = result.success && !structuredIndicatesError;
725
731
  await this.emitProgressEvent({
726
732
  sessionId: request.metadata?.sessionId || "unknown",
727
733
  timestamp: /* @__PURE__ */ new Date(),
728
734
  backend: "shell",
729
735
  count: ++this.eventCounter,
730
736
  type: "tool_result" /* TOOL_RESULT */,
731
- content: `${request.toolName} completed successfully (${duration}ms)`,
737
+ content: executionSucceeded ? `${request.toolName} completed successfully (${duration}ms)` : `${request.toolName} completed with error (${duration}ms)`,
732
738
  toolId,
733
739
  metadata: {
734
740
  toolName: request.toolName,
735
741
  duration,
736
- success: result.success,
742
+ success: executionSucceeded,
737
743
  phase: "completion"
738
744
  }
739
745
  });
740
- const structuredResult = this.buildStructuredOutput(subagentType, result);
741
746
  const toolResult = {
742
747
  content: structuredResult.content,
743
- status: result.success ? "completed" /* COMPLETED */ : "failed" /* FAILED */,
748
+ status: executionSucceeded ? "completed" /* COMPLETED */ : "failed" /* FAILED */,
744
749
  startTime: new Date(startTime),
745
750
  endTime: /* @__PURE__ */ new Date(),
746
751
  duration,
@@ -749,6 +754,9 @@ var init_shell_backend = __esm({
749
754
  };
750
755
  if (result.error) {
751
756
  toolResult.error = new Error(result.error);
757
+ } else if (!executionSucceeded) {
758
+ const structuredErrorMessage = typeof structuredPayload?.error === "string" && structuredPayload.error || typeof structuredPayload?.result === "string" && structuredPayload.result || `${request.toolName} reported a structured error`;
759
+ toolResult.error = new Error(structuredErrorMessage);
752
760
  }
753
761
  if (structuredResult.metadata) {
754
762
  toolResult.metadata = structuredResult.metadata;
@@ -1000,6 +1008,9 @@ var init_shell_backend = __esm({
1000
1008
  if (isPython && subagentType === "pi" && request.arguments?.live === true) {
1001
1009
  args.push("--live");
1002
1010
  }
1011
+ if (isPython && subagentType === "pi" && request.arguments?.liveInteractiveSession === true) {
1012
+ args.push("--live-manual");
1013
+ }
1003
1014
  if (isPython && this.config.debug) {
1004
1015
  args.push("--verbose");
1005
1016
  }
@@ -1282,8 +1293,19 @@ var init_shell_backend = __esm({
1282
1293
  if (subagentType === "pi") {
1283
1294
  const piEvent = result.subAgentResponse ?? this.extractLastJsonEvent(result.output);
1284
1295
  if (piEvent) {
1285
- let resultText = piEvent.result;
1286
- if (!resultText && Array.isArray(piEvent.messages)) {
1296
+ const piNestedEvent = typeof piEvent.sub_agent_response === "object" && piEvent.sub_agent_response ? piEvent.sub_agent_response : void 0;
1297
+ const piSessionId = typeof piEvent.session_id === "string" && piEvent.session_id ? piEvent.session_id : typeof piEvent.sessionId === "string" && piEvent.sessionId ? piEvent.sessionId : typeof piEvent.id === "string" && piEvent.type === "session" ? piEvent.id : typeof piNestedEvent?.session_id === "string" && piNestedEvent.session_id ? piNestedEvent.session_id : typeof piNestedEvent?.sessionId === "string" && piNestedEvent.sessionId ? piNestedEvent.sessionId : typeof piNestedEvent?.id === "string" && piNestedEvent.type === "session" ? piNestedEvent.id : typeof piEvent.sub_agent_response?.session_id === "string" && piEvent.sub_agent_response.session_id ? piEvent.sub_agent_response.session_id : void 0;
1298
+ const sanitizedPiEvent = { ...piEvent };
1299
+ delete sanitizedPiEvent.messages;
1300
+ if (sanitizedPiEvent.sub_agent_response && typeof sanitizedPiEvent.sub_agent_response === "object") {
1301
+ const inner = { ...sanitizedPiEvent.sub_agent_response };
1302
+ delete inner.messages;
1303
+ delete inner.type;
1304
+ sanitizedPiEvent.sub_agent_response = inner;
1305
+ }
1306
+ const hasDirectResultText = typeof piEvent.result === "string";
1307
+ let resultText = hasDirectResultText ? piEvent.result : void 0;
1308
+ if (resultText === void 0 && Array.isArray(piEvent.messages)) {
1287
1309
  for (let i = piEvent.messages.length - 1; i >= 0; i--) {
1288
1310
  const msg = piEvent.messages[i];
1289
1311
  if (msg?.role === "assistant") {
@@ -1303,16 +1325,11 @@ var init_shell_backend = __esm({
1303
1325
  }
1304
1326
  }
1305
1327
  }
1306
- if (resultText) {
1328
+ if (resultText === void 0 && typeof piEvent.error === "string") {
1329
+ resultText = piEvent.error;
1330
+ }
1331
+ if (resultText !== void 0) {
1307
1332
  const isError = piEvent.is_error ?? !result.success;
1308
- const sanitizedPiEvent = { ...piEvent };
1309
- delete sanitizedPiEvent.messages;
1310
- if (sanitizedPiEvent.sub_agent_response && typeof sanitizedPiEvent.sub_agent_response === "object") {
1311
- const inner = { ...sanitizedPiEvent.sub_agent_response };
1312
- delete inner.messages;
1313
- delete inner.type;
1314
- sanitizedPiEvent.sub_agent_response = inner;
1315
- }
1316
1333
  const usage = piEvent.usage;
1317
1334
  const totalCostUsd = typeof piEvent.total_cost_usd === "number" ? piEvent.total_cost_usd : typeof usage?.cost?.total === "number" ? usage.cost.total : void 0;
1318
1335
  const structuredPayload = {
@@ -1320,9 +1337,9 @@ var init_shell_backend = __esm({
1320
1337
  subtype: piEvent.subtype || (isError ? "error" : "success"),
1321
1338
  is_error: isError,
1322
1339
  result: resultText,
1323
- error: piEvent.error,
1340
+ error: isError ? piEvent.error ?? result.error ?? resultText : piEvent.error,
1324
1341
  stderr: result.error,
1325
- session_id: piEvent.session_id,
1342
+ session_id: piSessionId,
1326
1343
  exit_code: result.exitCode,
1327
1344
  duration_ms: piEvent.duration_ms ?? result.duration,
1328
1345
  total_cost_usd: totalCostUsd,
@@ -1340,6 +1357,57 @@ var init_shell_backend = __esm({
1340
1357
  metadata
1341
1358
  };
1342
1359
  }
1360
+ const isSessionSnapshotOnly = piEvent.type === "session" || piEvent.subtype === "session";
1361
+ if (isSessionSnapshotOnly) {
1362
+ const errorMessage = result.error?.trim() || "Pi exited before emitting a terminal result event (session snapshot only).";
1363
+ const structuredPayload = {
1364
+ type: "result",
1365
+ subtype: "error",
1366
+ is_error: true,
1367
+ result: errorMessage,
1368
+ error: errorMessage,
1369
+ stderr: result.error,
1370
+ session_id: piSessionId,
1371
+ exit_code: result.exitCode,
1372
+ duration_ms: result.duration,
1373
+ sub_agent_response: sanitizedPiEvent
1374
+ };
1375
+ const metadata = {
1376
+ ...piEvent ? { subAgentResponse: piEvent } : void 0,
1377
+ structuredOutput: true,
1378
+ contentType: "application/json",
1379
+ rawOutput: result.output
1380
+ };
1381
+ return {
1382
+ content: JSON.stringify(structuredPayload),
1383
+ metadata
1384
+ };
1385
+ }
1386
+ if (!result.success) {
1387
+ const errorMessage = result.error?.trim() || result.output?.trim() || "Unknown error";
1388
+ const structuredPayload = {
1389
+ type: "result",
1390
+ subtype: "error",
1391
+ is_error: true,
1392
+ result: errorMessage,
1393
+ error: errorMessage,
1394
+ stderr: result.error,
1395
+ session_id: piSessionId,
1396
+ exit_code: result.exitCode,
1397
+ duration_ms: result.duration,
1398
+ sub_agent_response: sanitizedPiEvent
1399
+ };
1400
+ const metadata = {
1401
+ ...piEvent ? { subAgentResponse: piEvent } : void 0,
1402
+ structuredOutput: true,
1403
+ contentType: "application/json",
1404
+ rawOutput: result.output
1405
+ };
1406
+ return {
1407
+ content: JSON.stringify(structuredPayload),
1408
+ metadata
1409
+ };
1410
+ }
1343
1411
  }
1344
1412
  }
1345
1413
  if (!result.success) {
@@ -1404,6 +1472,20 @@ var init_shell_backend = __esm({
1404
1472
  }
1405
1473
  return null;
1406
1474
  }
1475
+ /**
1476
+ * Parse JSON structured output payload emitted by shell service wrappers.
1477
+ */
1478
+ parseStructuredResultPayload(content) {
1479
+ try {
1480
+ const parsed = JSON.parse(content);
1481
+ if (!parsed || typeof parsed !== "object") {
1482
+ return null;
1483
+ }
1484
+ return parsed;
1485
+ } catch {
1486
+ return null;
1487
+ }
1488
+ }
1407
1489
  /**
1408
1490
  * Extract the last valid JSON object from a script's stdout to use as a structured payload fallback.
1409
1491
  */
@@ -1726,6 +1808,31 @@ var SUBAGENT_DEFAULT_MODELS = {
1726
1808
  cursor: "auto",
1727
1809
  pi: ":pi"
1728
1810
  };
1811
+ function isModelCompatibleWithSubagent(model, subagent) {
1812
+ if (!model.startsWith(":")) {
1813
+ return true;
1814
+ }
1815
+ const claudeShorthands = [":sonnet", ":haiku", ":opus"];
1816
+ const codexShorthands = [":codex", ":codex-mini", ":gpt-5", ":mini"];
1817
+ const geminiShorthands = [":pro", ":flash"];
1818
+ const isClaudeModel = claudeShorthands.includes(model) || model.startsWith(":claude");
1819
+ const isCodexModel = codexShorthands.includes(model) || model.startsWith(":gpt");
1820
+ const isGeminiModel = geminiShorthands.includes(model) || model.startsWith(":gemini");
1821
+ switch (subagent) {
1822
+ case "claude":
1823
+ return isClaudeModel || !isCodexModel && !isGeminiModel;
1824
+ case "codex":
1825
+ return isCodexModel || !isClaudeModel && !isGeminiModel;
1826
+ case "gemini":
1827
+ return isGeminiModel || !isClaudeModel && !isCodexModel;
1828
+ case "cursor":
1829
+ return true;
1830
+ case "pi":
1831
+ return true;
1832
+ default:
1833
+ return true;
1834
+ }
1835
+ }
1729
1836
 
1730
1837
  // src/core/config.ts
1731
1838
  var ENV_VAR_MAPPING = {
@@ -2249,6 +2356,13 @@ async function ensureHooksConfig(baseDir) {
2249
2356
  existingConfig.defaultModels = baseDefaults;
2250
2357
  needsUpdate = true;
2251
2358
  }
2359
+ const selectedSubagentRaw = typeof existingConfig.defaultSubagent === "string" ? existingConfig.defaultSubagent : "claude";
2360
+ const selectedSubagent = selectedSubagentRaw in SUBAGENT_DEFAULT_MODELS ? selectedSubagentRaw : "claude";
2361
+ const selectedMapModel = existingConfig.defaultModels && typeof existingConfig.defaultModels === "object" ? existingConfig.defaultModels[selectedSubagent] : void 0;
2362
+ if (typeof selectedMapModel === "string" && isModelCompatibleWithSubagent(selectedMapModel, selectedSubagent) && existingConfig.defaultModel !== selectedMapModel) {
2363
+ existingConfig.defaultModel = selectedMapModel;
2364
+ needsUpdate = true;
2365
+ }
2252
2366
  if (existingConfig.defaultMaxIterations === 50) {
2253
2367
  existingConfig.defaultMaxIterations = DEFAULT_CONFIG.defaultMaxIterations;
2254
2368
  needsUpdate = true;
@@ -2553,6 +2667,178 @@ function validateHooksConfig(hooks) {
2553
2667
  // src/core/engine.ts
2554
2668
  init_advanced_logger();
2555
2669
  init_shell_backend();
2670
+
2671
+ // src/core/prompt-command-substitution.ts
2672
+ init_version();
2673
+ var SINGLE_QUOTED_MARKER = "!'";
2674
+ var TRIPLE_BACKTICK_MARKER = "!```";
2675
+ var TRIPLE_BACKTICK_CLOSER = "```";
2676
+ var DEFAULT_MAX_BUFFER_BYTES = 1024 * 1024;
2677
+ var DEFAULT_COMMAND_TIMEOUT_MS = 3e4;
2678
+ var COMMAND_TIMEOUT_ENV_KEY = "JUNO_CODE_PROMPT_SUBSTITUTION_TIMEOUT_MS";
2679
+ function findPromptCommandSubstitutions(prompt) {
2680
+ const matches = [];
2681
+ let cursor = 0;
2682
+ while (cursor < prompt.length) {
2683
+ const singleQuotedStart = prompt.indexOf(SINGLE_QUOTED_MARKER, cursor);
2684
+ const tripleBacktickStart = prompt.indexOf(TRIPLE_BACKTICK_MARKER, cursor);
2685
+ const markerStart = chooseNearestMarker(singleQuotedStart, tripleBacktickStart);
2686
+ if (markerStart === null) {
2687
+ break;
2688
+ }
2689
+ if (markerStart === singleQuotedStart) {
2690
+ const parsedSingleQuoted = parseSingleQuotedSubstitution(prompt, markerStart);
2691
+ if (!parsedSingleQuoted) {
2692
+ cursor = markerStart + SINGLE_QUOTED_MARKER.length;
2693
+ continue;
2694
+ }
2695
+ matches.push(parsedSingleQuoted);
2696
+ cursor = parsedSingleQuoted.endIndex;
2697
+ continue;
2698
+ }
2699
+ const parsedTripleBacktick = parseTripleBacktickSubstitution(prompt, markerStart);
2700
+ if (!parsedTripleBacktick) {
2701
+ cursor = markerStart + TRIPLE_BACKTICK_MARKER.length;
2702
+ continue;
2703
+ }
2704
+ matches.push(parsedTripleBacktick);
2705
+ cursor = parsedTripleBacktick.endIndex;
2706
+ }
2707
+ return matches;
2708
+ }
2709
+ async function resolvePromptCommandSubstitutions(prompt, options) {
2710
+ const matches = findPromptCommandSubstitutions(prompt);
2711
+ if (matches.length === 0) {
2712
+ return prompt;
2713
+ }
2714
+ const executor = options.executor ?? createDefaultPromptCommandExecutor(options);
2715
+ let result = "";
2716
+ let cursor = 0;
2717
+ for (const match of matches) {
2718
+ result += prompt.slice(cursor, match.startIndex);
2719
+ const commandOutput = await executor(match.command);
2720
+ result += normalizeCommandOutput(commandOutput);
2721
+ cursor = match.endIndex;
2722
+ }
2723
+ result += prompt.slice(cursor);
2724
+ return result;
2725
+ }
2726
+ function chooseNearestMarker(singleQuotedStart, tripleBacktickStart) {
2727
+ const singleExists = singleQuotedStart >= 0;
2728
+ const tripleExists = tripleBacktickStart >= 0;
2729
+ if (!singleExists && !tripleExists) {
2730
+ return null;
2731
+ }
2732
+ if (!singleExists) {
2733
+ return tripleBacktickStart;
2734
+ }
2735
+ if (!tripleExists) {
2736
+ return singleQuotedStart;
2737
+ }
2738
+ return Math.min(singleQuotedStart, tripleBacktickStart);
2739
+ }
2740
+ function parseSingleQuotedSubstitution(prompt, markerStart) {
2741
+ const contentStart = markerStart + SINGLE_QUOTED_MARKER.length;
2742
+ const closingQuote = findClosingSingleQuote(prompt, contentStart);
2743
+ if (closingQuote < 0) {
2744
+ return null;
2745
+ }
2746
+ const raw = prompt.slice(markerStart, closingQuote + 1);
2747
+ const command = prompt.slice(contentStart, closingQuote);
2748
+ return {
2749
+ syntax: "single-quoted",
2750
+ startIndex: markerStart,
2751
+ endIndex: closingQuote + 1,
2752
+ command,
2753
+ raw
2754
+ };
2755
+ }
2756
+ function findClosingSingleQuote(prompt, startIndex) {
2757
+ let escaped = false;
2758
+ for (let index = startIndex; index < prompt.length; index++) {
2759
+ const char = prompt[index];
2760
+ if (char === "'" && !escaped) {
2761
+ return index;
2762
+ }
2763
+ if (char === "\\" && !escaped) {
2764
+ escaped = true;
2765
+ continue;
2766
+ }
2767
+ escaped = false;
2768
+ }
2769
+ return -1;
2770
+ }
2771
+ function parseTripleBacktickSubstitution(prompt, markerStart) {
2772
+ const contentStart = markerStart + TRIPLE_BACKTICK_MARKER.length;
2773
+ const closingBackticks = prompt.indexOf(TRIPLE_BACKTICK_CLOSER, contentStart);
2774
+ if (closingBackticks < 0) {
2775
+ return null;
2776
+ }
2777
+ const raw = prompt.slice(markerStart, closingBackticks + TRIPLE_BACKTICK_CLOSER.length);
2778
+ const command = prompt.slice(contentStart, closingBackticks);
2779
+ return {
2780
+ syntax: "triple-backtick",
2781
+ startIndex: markerStart,
2782
+ endIndex: closingBackticks + TRIPLE_BACKTICK_CLOSER.length,
2783
+ command,
2784
+ raw
2785
+ };
2786
+ }
2787
+ function createDefaultPromptCommandExecutor(options) {
2788
+ const execFile2 = promisify(childProcess.execFile);
2789
+ const maxBufferBytes = options.maxBufferBytes ?? DEFAULT_MAX_BUFFER_BYTES;
2790
+ const commandTimeoutMs = resolvePromptCommandTimeoutMs(options.commandTimeoutMs);
2791
+ const shell = process.env.SHELL || "/bin/bash";
2792
+ return async (command) => {
2793
+ const normalizedCommand = command.trim();
2794
+ if (!normalizedCommand) {
2795
+ return "";
2796
+ }
2797
+ const commandForExecution = wrapCommandForNonInteractiveExecution(normalizedCommand);
2798
+ try {
2799
+ const result = await execFile2(shell, ["-lc", commandForExecution], {
2800
+ cwd: options.workingDirectory,
2801
+ env: options.environment ?? process.env,
2802
+ maxBuffer: maxBufferBytes,
2803
+ timeout: commandTimeoutMs
2804
+ });
2805
+ const stdout2 = typeof result === "string" || Buffer.isBuffer(result) ? String(result) : String(result.stdout ?? "");
2806
+ return stdout2;
2807
+ } catch (error) {
2808
+ const failedCommand = normalizedCommand.replace(/\s+/g, " ").trim();
2809
+ const details = error && typeof error === "object" && "stderr" in error ? String(error.stderr ?? "").trim() : "";
2810
+ const timeoutDetected = error && typeof error === "object" && (("code" in error ? String(error.code ?? "").toUpperCase() === "ETIMEDOUT" : false) || "killed" in error && Boolean(error.killed) && String(error.signal ?? "").toUpperCase() === "SIGTERM" || "message" in error && /timed?\s*out/i.test(String(error.message ?? "")));
2811
+ if (timeoutDetected) {
2812
+ throw new Error(
2813
+ `Prompt command substitution timed out after ${commandTimeoutMs}ms for \`${failedCommand}\``
2814
+ );
2815
+ }
2816
+ const suffix = details ? `: ${details}` : "";
2817
+ throw new Error(`Prompt command substitution failed for \`${failedCommand}\`${suffix}`);
2818
+ }
2819
+ };
2820
+ }
2821
+ function resolvePromptCommandTimeoutMs(explicitTimeoutMs) {
2822
+ if (typeof explicitTimeoutMs === "number" && Number.isFinite(explicitTimeoutMs) && explicitTimeoutMs > 0) {
2823
+ return explicitTimeoutMs;
2824
+ }
2825
+ const envValue = process.env[COMMAND_TIMEOUT_ENV_KEY];
2826
+ if (envValue !== void 0) {
2827
+ const parsed = Number(envValue);
2828
+ if (Number.isFinite(parsed) && parsed > 0) {
2829
+ return parsed;
2830
+ }
2831
+ }
2832
+ return DEFAULT_COMMAND_TIMEOUT_MS;
2833
+ }
2834
+ function wrapCommandForNonInteractiveExecution(command) {
2835
+ return `(${command}) </dev/null`;
2836
+ }
2837
+ function normalizeCommandOutput(output) {
2838
+ return output.replace(/\r?\n$/, "");
2839
+ }
2840
+
2841
+ // src/core/engine.ts
2556
2842
  var ExecutionStatus = /* @__PURE__ */ ((ExecutionStatus2) => {
2557
2843
  ExecutionStatus2["PENDING"] = "pending";
2558
2844
  ExecutionStatus2["RUNNING"] = "running";
@@ -2859,7 +3145,8 @@ var ExecutionEngine = class extends EventEmitter {
2859
3145
  if (!request.requestId?.trim()) {
2860
3146
  throw new Error("Request ID is required");
2861
3147
  }
2862
- if (!request.instruction?.trim()) {
3148
+ const allowEmptyInstructionForPiLiveInteractiveSession = request.subagent === "pi" && request.live === true && request.liveInteractiveSession === true && typeof request.resume === "string" && request.resume.trim().length > 0;
3149
+ if (!request.instruction?.trim() && !allowEmptyInstructionForPiLiveInteractiveSession) {
2863
3150
  throw new Error("Instruction is required");
2864
3151
  }
2865
3152
  if (!request.subagent?.trim()) {
@@ -3097,44 +3384,62 @@ var ExecutionEngine = class extends EventEmitter {
3097
3384
  engineLogger.warn("Hook START_ITERATION failed", { error, iterationNumber });
3098
3385
  }
3099
3386
  this.emit("iteration:start", { context, iterationNumber });
3100
- const toolRequest = {
3101
- toolName: this.getToolNameForSubagent(context.request.subagent),
3102
- arguments: {
3103
- instruction: context.request.instruction,
3104
- project_path: context.request.workingDirectory,
3105
- ...context.request.model !== void 0 && { model: context.request.model },
3106
- ...context.request.agents !== void 0 && { agents: context.request.agents },
3107
- ...context.request.tools !== void 0 && { tools: context.request.tools },
3108
- ...context.request.allowedTools !== void 0 && {
3109
- allowedTools: context.request.allowedTools
3110
- },
3111
- ...context.request.appendAllowedTools !== void 0 && {
3112
- appendAllowedTools: context.request.appendAllowedTools
3113
- },
3114
- ...context.request.disallowedTools !== void 0 && {
3115
- disallowedTools: context.request.disallowedTools
3387
+ let toolRequest = null;
3388
+ try {
3389
+ const instructionTemplate = context.request.instruction;
3390
+ const resolvedInstruction = await resolvePromptCommandSubstitutions(instructionTemplate, {
3391
+ workingDirectory: context.request.workingDirectory,
3392
+ environment: {
3393
+ ...process.env,
3394
+ JUNO_TASK_ROOT: process.env.JUNO_TASK_ROOT || context.request.workingDirectory
3395
+ }
3396
+ });
3397
+ this.emit("iteration:instruction-resolved", {
3398
+ context,
3399
+ iterationNumber,
3400
+ instruction: resolvedInstruction,
3401
+ templateInstruction: instructionTemplate
3402
+ });
3403
+ toolRequest = {
3404
+ toolName: this.getToolNameForSubagent(context.request.subagent),
3405
+ arguments: {
3406
+ instruction: resolvedInstruction,
3407
+ project_path: context.request.workingDirectory,
3408
+ ...context.request.model !== void 0 && { model: context.request.model },
3409
+ ...context.request.agents !== void 0 && { agents: context.request.agents },
3410
+ ...context.request.tools !== void 0 && { tools: context.request.tools },
3411
+ ...context.request.allowedTools !== void 0 && {
3412
+ allowedTools: context.request.allowedTools
3413
+ },
3414
+ ...context.request.appendAllowedTools !== void 0 && {
3415
+ appendAllowedTools: context.request.appendAllowedTools
3416
+ },
3417
+ ...context.request.disallowedTools !== void 0 && {
3418
+ disallowedTools: context.request.disallowedTools
3419
+ },
3420
+ ...context.request.resume !== void 0 && { resume: context.request.resume },
3421
+ ...context.request.continueConversation !== void 0 && {
3422
+ continueConversation: context.request.continueConversation
3423
+ },
3424
+ ...context.request.thinking !== void 0 && { thinking: context.request.thinking },
3425
+ ...context.request.live !== void 0 && { live: context.request.live },
3426
+ ...context.request.liveInteractiveSession !== void 0 && {
3427
+ liveInteractiveSession: context.request.liveInteractiveSession
3428
+ },
3429
+ iteration: iterationNumber
3116
3430
  },
3117
- ...context.request.resume !== void 0 && { resume: context.request.resume },
3118
- ...context.request.continueConversation !== void 0 && {
3119
- continueConversation: context.request.continueConversation
3431
+ timeout: context.request.timeoutMs || this.engineConfig.config.mcpTimeout,
3432
+ priority: context.request.priority || "normal",
3433
+ metadata: {
3434
+ sessionId: context.sessionContext.sessionId,
3435
+ iterationNumber
3120
3436
  },
3121
- ...context.request.thinking !== void 0 && { thinking: context.request.thinking },
3122
- ...context.request.live !== void 0 && { live: context.request.live },
3123
- iteration: iterationNumber
3124
- },
3125
- timeout: context.request.timeoutMs || this.engineConfig.config.mcpTimeout,
3126
- priority: context.request.priority || "normal",
3127
- metadata: {
3128
- sessionId: context.sessionContext.sessionId,
3129
- iterationNumber
3130
- },
3131
- progressCallback: async (event) => {
3132
- context.progressEvents.push(event);
3133
- context.statistics.totalProgressEvents++;
3134
- await this.processProgressEvent(context, event);
3135
- }
3136
- };
3137
- try {
3437
+ progressCallback: async (event) => {
3438
+ context.progressEvents.push(event);
3439
+ context.statistics.totalProgressEvents++;
3440
+ await this.processProgressEvent(context, event);
3441
+ }
3442
+ };
3138
3443
  if (!this.currentBackend) {
3139
3444
  throw new Error("No backend initialized. Call initializeBackend() first.");
3140
3445
  }
@@ -3203,7 +3508,10 @@ var ExecutionEngine = class extends EventEmitter {
3203
3508
  duration,
3204
3509
  error: mcpError,
3205
3510
  progressEvents: [],
3206
- request: toolRequest
3511
+ request: toolRequest ?? {
3512
+ toolName: this.getToolNameForSubagent(context.request.subagent),
3513
+ arguments: {}
3514
+ }
3207
3515
  },
3208
3516
  progressEvents: [],
3209
3517
  error: mcpError
@@ -3718,6 +4026,9 @@ function createExecutionRequest(options) {
3718
4026
  if (options.live !== void 0) {
3719
4027
  result.live = options.live;
3720
4028
  }
4029
+ if (options.liveInteractiveSession !== void 0) {
4030
+ result.liveInteractiveSession = options.liveInteractiveSession;
4031
+ }
3721
4032
  return result;
3722
4033
  }
3723
4034