@vtxmacro/cli 2026.10.32 → 2026.10.34

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/bin/vtx.js CHANGED
@@ -113,7 +113,7 @@ var init_routing = __esm({
113
113
  var agent_cli_release_default;
114
114
  var init_agent_cli_release = __esm({
115
115
  "agent-cli-release.json"() {
116
- agent_cli_release_default = { package_name: "@vtxmacro/cli", package_version: "2026.10.32", codex_package_name: "@openai/codex", codex_version: "0.155.0", copilot_sdk_package_name: "@github/copilot-sdk", copilot_sdk_version: "1.0.0-beta.8", copilot_cli_package_name: "@github/copilot", copilot_cli_version: "1.0.80", deepseek_harness_version: "0.1.1-rc.2", deepseek_harness_packages: ["@deepseek-ai/dsh-agent", "@deepseek-ai/dsh-agent-instructions", "@deepseek-ai/dsh-agent-loop", "@deepseek-ai/dsh-agent-spine-demo", "@deepseek-ai/dsh-anonymous-user-id", "@deepseek-ai/dsh-atomic-write", "@deepseek-ai/dsh-attachment", "@deepseek-ai/dsh-brand", "@deepseek-ai/dsh-code-runtime", "@deepseek-ai/dsh-credentials", "@deepseek-ai/dsh-fs", "@deepseek-ai/dsh-goal", "@deepseek-ai/dsh-goal-round-driver", "@deepseek-ai/dsh-home-paths", "@deepseek-ai/dsh-invariants", "@deepseek-ai/dsh-jobs", "@deepseek-ai/dsh-jobs-local", "@deepseek-ai/dsh-launch-environment", "@deepseek-ai/dsh-llm", "@deepseek-ai/dsh-llm-deepseek", "@deepseek-ai/dsh-llm-retry", "@deepseek-ai/dsh-output-retention", "@deepseek-ai/dsh-sandbox", "@deepseek-ai/dsh-sandbox-policy", "@deepseek-ai/dsh-scope", "@deepseek-ai/dsh-session", "@deepseek-ai/dsh-session-checkpoint-policy", "@deepseek-ai/dsh-session-persistence", "@deepseek-ai/dsh-session-persistence-jsonl", "@deepseek-ai/dsh-session-projection", "@deepseek-ai/dsh-session-title", "@deepseek-ai/dsh-settings", "@deepseek-ai/dsh-shell", "@deepseek-ai/dsh-shell-env", "@deepseek-ai/dsh-skill", "@deepseek-ai/dsh-skill-filesystem", "@deepseek-ai/dsh-subprocess", "@deepseek-ai/dsh-system-prompt", "@deepseek-ai/dsh-timeout", "@deepseek-ai/dsh-tool-bash", "@deepseek-ai/dsh-tool-goal", "@deepseek-ai/dsh-tool-jobs", "@deepseek-ai/dsh-tool-skill", "@deepseek-ai/dsh-tools", "@deepseek-ai/dsh-typert-protocol", "@deepseek-ai/dsh-user-approval"], deepseek_cordis_package_name: "@deepseek-ai/cordis", deepseek_cordis_version: "4.0.1", deepseek_support_packages: { "@deepseek-ai/cordis-plugin-timer": "1.1.3" }, platforms: { "linux-x64": { package_name: "@openai/codex-linux-x64", target: "x86_64-unknown-linux-musl", binary_name: "codex", sha256: "660e159a49e823ac8e5986cb238f73158ce4b957d40d9292f8de90862644b501" }, "win32-x64": { package_name: "@openai/codex-win32-x64", target: "x86_64-pc-windows-msvc", binary_name: "codex.exe", sha256: "e4c11374bd9de8ad5c3b7617fd4654bb7839901edb0863f9930666863c7a021b" } }, pi_coding_agent_package_name: "@earendil-works/pi-coding-agent", pi_ai_package_name: "@earendil-works/pi-ai", pi_version: "0.85.1", pi_support_packages: ["@earendil-works/pi-agent-core", "@earendil-works/pi-telemetry", "@earendil-works/pi-tui", "@earendil-works/chord"], grok_version: "1.0.30", grok_platforms: { "linux-x64": { package_name: "@xai-official/grok-linux-x64", binary_name: "grok", sha256: "504dd6546ab991b75d36698242875ce461489cd1f8cd84285873cb55bd5c7d54" }, "win32-x64": { package_name: "@xai-official/grok-win32-x64", binary_name: "grok.exe", sha256: "48736d1a4342a801ea26d0ecde4c516b653f791399065adaa55973f83abd8867" } } };
116
+ agent_cli_release_default = { package_name: "@vtxmacro/cli", package_version: "2026.10.34", codex_package_name: "@openai/codex", codex_version: "0.155.0", copilot_sdk_package_name: "@github/copilot-sdk", copilot_sdk_version: "1.0.0-beta.8", copilot_cli_package_name: "@github/copilot", copilot_cli_version: "1.0.80", deepseek_harness_version: "0.1.1-rc.2", deepseek_harness_packages: ["@deepseek-ai/dsh-agent", "@deepseek-ai/dsh-agent-instructions", "@deepseek-ai/dsh-agent-loop", "@deepseek-ai/dsh-agent-spine-demo", "@deepseek-ai/dsh-anonymous-user-id", "@deepseek-ai/dsh-atomic-write", "@deepseek-ai/dsh-attachment", "@deepseek-ai/dsh-brand", "@deepseek-ai/dsh-code-runtime", "@deepseek-ai/dsh-credentials", "@deepseek-ai/dsh-fs", "@deepseek-ai/dsh-goal", "@deepseek-ai/dsh-goal-round-driver", "@deepseek-ai/dsh-home-paths", "@deepseek-ai/dsh-invariants", "@deepseek-ai/dsh-jobs", "@deepseek-ai/dsh-jobs-local", "@deepseek-ai/dsh-launch-environment", "@deepseek-ai/dsh-llm", "@deepseek-ai/dsh-llm-deepseek", "@deepseek-ai/dsh-llm-retry", "@deepseek-ai/dsh-output-retention", "@deepseek-ai/dsh-sandbox", "@deepseek-ai/dsh-sandbox-policy", "@deepseek-ai/dsh-scope", "@deepseek-ai/dsh-session", "@deepseek-ai/dsh-session-checkpoint-policy", "@deepseek-ai/dsh-session-persistence", "@deepseek-ai/dsh-session-persistence-jsonl", "@deepseek-ai/dsh-session-projection", "@deepseek-ai/dsh-session-title", "@deepseek-ai/dsh-settings", "@deepseek-ai/dsh-shell", "@deepseek-ai/dsh-shell-env", "@deepseek-ai/dsh-skill", "@deepseek-ai/dsh-skill-filesystem", "@deepseek-ai/dsh-subprocess", "@deepseek-ai/dsh-system-prompt", "@deepseek-ai/dsh-timeout", "@deepseek-ai/dsh-tool-bash", "@deepseek-ai/dsh-tool-goal", "@deepseek-ai/dsh-tool-jobs", "@deepseek-ai/dsh-tool-skill", "@deepseek-ai/dsh-tools", "@deepseek-ai/dsh-typert-protocol", "@deepseek-ai/dsh-user-approval"], deepseek_cordis_package_name: "@deepseek-ai/cordis", deepseek_cordis_version: "4.0.1", deepseek_support_packages: { "@deepseek-ai/cordis-plugin-timer": "1.1.3" }, platforms: { "linux-x64": { package_name: "@openai/codex-linux-x64", target: "x86_64-unknown-linux-musl", binary_name: "codex", sha256: "660e159a49e823ac8e5986cb238f73158ce4b957d40d9292f8de90862644b501" }, "win32-x64": { package_name: "@openai/codex-win32-x64", target: "x86_64-pc-windows-msvc", binary_name: "codex.exe", sha256: "e4c11374bd9de8ad5c3b7617fd4654bb7839901edb0863f9930666863c7a021b" } }, pi_coding_agent_package_name: "@earendil-works/pi-coding-agent", pi_ai_package_name: "@earendil-works/pi-ai", pi_version: "0.85.1", pi_support_packages: ["@earendil-works/pi-agent-core", "@earendil-works/pi-telemetry", "@earendil-works/pi-tui", "@earendil-works/chord"], grok_version: "1.0.30", grok_platforms: { "linux-x64": { package_name: "@xai-official/grok-linux-x64", binary_name: "grok", sha256: "504dd6546ab991b75d36698242875ce461489cd1f8cd84285873cb55bd5c7d54" }, "win32-x64": { package_name: "@xai-official/grok-win32-x64", binary_name: "grok.exe", sha256: "48736d1a4342a801ea26d0ecde4c516b653f791399065adaa55973f83abd8867" } } };
117
117
  }
118
118
  });
119
119
 
@@ -1195,6 +1195,7 @@ var init_runtime_policy_generated = __esm({
1195
1195
  runtime: {
1196
1196
  assignment_page_default_limit: 20,
1197
1197
  client_candidate_owner_lease_grace_ms: 6e4,
1198
+ bot_switch_max_retries: 2,
1198
1199
  client_server_heartbeats_per_owner_lease: 2,
1199
1200
  client_server_heartbeat_min_ms: 5e3,
1200
1201
  client_server_heartbeat_max_ms: 3e4
@@ -3890,10 +3891,10 @@ while(($line=[Console]::In.ReadLine()) -ne $null) {
3890
3891
  env: invocation.env
3891
3892
  });
3892
3893
  const output3 = [];
3893
- let settled = false;
3894
+ let settled2 = false;
3894
3895
  const settle = (value) => {
3895
- if (settled) return;
3896
- settled = true;
3896
+ if (settled2) return;
3897
+ settled2 = true;
3897
3898
  clearTimeout(timer);
3898
3899
  resolvePromise(value);
3899
3900
  };
@@ -3920,10 +3921,10 @@ while(($line=[Console]::In.ReadLine()) -ne $null) {
3920
3921
  stdio: ["ignore", "pipe", "ignore"]
3921
3922
  });
3922
3923
  const output3 = [];
3923
- let settled = false;
3924
+ let settled2 = false;
3924
3925
  const settle = (value) => {
3925
- if (settled) return;
3926
- settled = true;
3926
+ if (settled2) return;
3927
+ settled2 = true;
3927
3928
  clearTimeout(timer);
3928
3929
  resolvePromise(value);
3929
3930
  };
@@ -3946,10 +3947,10 @@ while(($line=[Console]::In.ReadLine()) -ne $null) {
3946
3947
  });
3947
3948
  const output3 = [];
3948
3949
  let bytes3 = 0;
3949
- let settled = false;
3950
+ let settled2 = false;
3950
3951
  const settle = (value) => {
3951
- if (settled) return;
3952
- settled = true;
3952
+ if (settled2) return;
3953
+ settled2 = true;
3953
3954
  clearTimeout(timer);
3954
3955
  resolvePromise(value);
3955
3956
  };
@@ -4334,6 +4335,165 @@ while(($line=[Console]::In.ReadLine()) -ne $null) {
4334
4335
  }
4335
4336
  });
4336
4337
 
4338
+ // lib/runtime/abort.ts
4339
+ var ABORT_MESSAGE_TOKENS, readAbortLikeMessage, isAbortLikeError, toAbortError;
4340
+ var init_abort = __esm({
4341
+ "lib/runtime/abort.ts"() {
4342
+ "use strict";
4343
+ init_define_VTX_EXO_POLICY();
4344
+ init_define_VTX_GROK_POLICY();
4345
+ init_define_VTX_PI_MODEL_POLICY();
4346
+ ABORT_MESSAGE_TOKENS = [
4347
+ "the operation was aborted",
4348
+ "the user aborted a request",
4349
+ "request was aborted",
4350
+ "request aborted",
4351
+ "signal is aborted",
4352
+ "client runtime stop requested"
4353
+ ];
4354
+ readAbortLikeMessage = (error48) => {
4355
+ if (error48 instanceof Error) {
4356
+ return error48.message;
4357
+ }
4358
+ if (typeof error48 === "string") {
4359
+ return error48;
4360
+ }
4361
+ if (error48 && typeof error48 === "object" && typeof error48.message === "string") {
4362
+ return String(error48.message);
4363
+ }
4364
+ return "";
4365
+ };
4366
+ isAbortLikeError = (error48) => {
4367
+ if (typeof DOMException !== "undefined" && error48 instanceof DOMException) {
4368
+ return error48.name === "AbortError";
4369
+ }
4370
+ if (error48 instanceof Error && error48.name === "AbortError") {
4371
+ return true;
4372
+ }
4373
+ if (error48 && typeof error48 === "object" && error48.name === "AbortError") {
4374
+ return true;
4375
+ }
4376
+ const normalized = readAbortLikeMessage(error48).trim().toLowerCase();
4377
+ if (!normalized) {
4378
+ return false;
4379
+ }
4380
+ return ABORT_MESSAGE_TOKENS.some((token) => normalized.includes(token));
4381
+ };
4382
+ toAbortError = (error48, fallbackMessage = "The operation was aborted.") => {
4383
+ const message = readAbortLikeMessage(error48).trim() || fallbackMessage;
4384
+ try {
4385
+ return new DOMException(message, "AbortError");
4386
+ } catch {
4387
+ const fallback = new Error(message);
4388
+ fallback.name = "AbortError";
4389
+ return fallback;
4390
+ }
4391
+ };
4392
+ }
4393
+ });
4394
+
4395
+ // lib/runtime/runtime-redaction.ts
4396
+ var REDACTED_VALUE, WHITESPACE_CLASS, SEPARATOR, VALUE_RUN, NAME_LETTER_VARIANTS, NAME_START, NAME_PREFIX, secretName, SECRET_NAME_WORDS, NAMED_VALUE, SECRET_QUERY_PARAM_PATTERN, BEARER_TOKEN_PATTERN, ASSIGNMENT_SEPARATOR, AUTHORIZATION_SCHEMES, assignmentPattern, SECRET_ASSIGNMENT_PATTERN, SECRET_WORD_ASSIGNMENT_PATTERN, SECRET_TOKEN_PATTERN, redactAssignedValue, isRuntimeErrorObject, sanitizeRuntimeDiagnosticValue, sanitizeRuntimeNetworkPath, getSanitizedRuntimeErrorMessage, toSanitizedRuntimeError, getSanitizedRuntimeAbortReason;
4397
+ var init_runtime_redaction = __esm({
4398
+ "lib/runtime/runtime-redaction.ts"() {
4399
+ "use strict";
4400
+ init_define_VTX_EXO_POLICY();
4401
+ init_define_VTX_GROK_POLICY();
4402
+ init_define_VTX_PI_MODEL_POLICY();
4403
+ init_abort();
4404
+ REDACTED_VALUE = "[REDACTED]";
4405
+ WHITESPACE_CLASS = String.raw`[\t\n\v\f\r \x1c-\x1f\x85\xa0\u1680\u2000-\u200a\u2028\u2029\u202f\u205f\u3000\ufeff]`;
4406
+ SEPARATOR = WHITESPACE_CLASS;
4407
+ VALUE_RUN = String.raw`[^,\t\n\v\f\r ]+`;
4408
+ NAME_LETTER_VARIANTS = {
4409
+ s: String.raw`[s\u017f]`,
4410
+ k: String.raw`[k\u212a]`,
4411
+ i: String.raw`[i\u0131\u0130]`
4412
+ };
4413
+ NAME_START = "(?:^|[^A-Za-z0-9_.-])";
4414
+ NAME_PREFIX = "[A-Za-z0-9_.-]*";
4415
+ secretName = (word) => Array.from(word, (letter) => NAME_LETTER_VARIANTS[letter] ?? letter).join("");
4416
+ SECRET_NAME_WORDS = `(?:${[
4417
+ "key",
4418
+ "token",
4419
+ "secret",
4420
+ "password",
4421
+ "passphrase",
4422
+ "credentials",
4423
+ "credential",
4424
+ "authorization"
4425
+ ].map(secretName).join("|")})`;
4426
+ NAMED_VALUE = String.raw`("[^"]*"|'[^']*'` + String.raw`|(?:[^,\t\n\v\f\r ]*${SECRET_NAME_WORDS}(?:[:=]${SEPARATOR}+|${SEPARATOR}+[:=]${SEPARATOR}*))*${VALUE_RUN})`;
4427
+ SECRET_QUERY_PARAM_PATTERN = new RegExp(
4428
+ `([?&](?:${NAME_PREFIX}${SECRET_NAME_WORDS}|${secretName("auth")}|${secretName("sig")}|${secretName("signature")})=)${NAMED_VALUE}`,
4429
+ "gi"
4430
+ );
4431
+ BEARER_TOKEN_PATTERN = new RegExp(
4432
+ String.raw`(\bBearer${SEPARATOR}+)(?:[^,;\t\n\v\f\r ]*${SECRET_NAME_WORDS}(?:[:=]${SEPARATOR}+|${SEPARATOR}+[:=]${SEPARATOR}*))*[^,;\t\n\v\f\r ]+`,
4433
+ "gi"
4434
+ );
4435
+ ASSIGNMENT_SEPARATOR = `['"]?${SEPARATOR}*[:=]${SEPARATOR}*`;
4436
+ AUTHORIZATION_SCHEMES = "(?:Bearer|Basic|Digest|Token|Bot|Negotiate|NTLM|ApiKey)";
4437
+ assignmentPattern = (nameStart) => new RegExp(
4438
+ `(${nameStart}(?:${secretName("authorization")}${ASSIGNMENT_SEPARATOR}['"]?${AUTHORIZATION_SCHEMES}${SEPARATOR}+|${SECRET_NAME_WORDS}${ASSIGNMENT_SEPARATOR}))${NAMED_VALUE}`,
4439
+ "gi"
4440
+ );
4441
+ SECRET_ASSIGNMENT_PATTERN = assignmentPattern(`${NAME_START}${NAME_PREFIX}`);
4442
+ SECRET_WORD_ASSIGNMENT_PATTERN = assignmentPattern(
4443
+ `(?:^|[^A-Za-z0-9_])(?:(?:${["api", "access", "private"].map(secretName).join("|")})[_ -]?)?`
4444
+ );
4445
+ SECRET_TOKEN_PATTERN = /\b(?:AIza[A-Za-z0-9_-]+|sk-[A-Za-z0-9._-]+|xai-[A-Za-z0-9]{20,}|gsk_[A-Za-z0-9]{20,}|AQ\.[A-Za-z0-9._-]+|0x[a-fA-F0-9]{64})\b/g;
4446
+ redactAssignedValue = (_match, prefix, value) => {
4447
+ const quote = value[0] === '"' || value[0] === "'" ? value[0] : "";
4448
+ const closing = quote && value.length > 1 && value[value.length - 1] === quote ? quote : "";
4449
+ return `${prefix}${quote}${REDACTED_VALUE}${closing}`;
4450
+ };
4451
+ isRuntimeErrorObject = (error48) => error48 instanceof Error || error48 != null && typeof error48 === "object" && Object.prototype.toString.call(error48) === "[object DOMException]" && typeof error48.message === "string" && typeof error48.name === "string";
4452
+ sanitizeRuntimeDiagnosticValue = (value) => {
4453
+ const normalized = String(value || "");
4454
+ if (!normalized) {
4455
+ return normalized;
4456
+ }
4457
+ return normalized.replace(BEARER_TOKEN_PATTERN, `$1${REDACTED_VALUE}`).replace(SECRET_WORD_ASSIGNMENT_PATTERN, redactAssignedValue).replace(SECRET_TOKEN_PATTERN, REDACTED_VALUE).replace(SECRET_QUERY_PARAM_PATTERN, redactAssignedValue).replace(SECRET_ASSIGNMENT_PATTERN, redactAssignedValue);
4458
+ };
4459
+ sanitizeRuntimeNetworkPath = (value) => {
4460
+ const normalized = String(value || "").trim();
4461
+ if (!normalized) {
4462
+ return "/";
4463
+ }
4464
+ const withoutFragment = normalized.split("#", 1)[0] || normalized;
4465
+ const withoutQuery = withoutFragment.split("?", 1)[0] || withoutFragment;
4466
+ const sanitized = sanitizeRuntimeDiagnosticValue(withoutQuery.trim());
4467
+ return sanitized || "/";
4468
+ };
4469
+ getSanitizedRuntimeErrorMessage = (error48) => {
4470
+ const message = isRuntimeErrorObject(error48) ? error48.message : typeof error48 === "string" ? error48 : error48 == null ? null : String(error48);
4471
+ if (message == null) {
4472
+ return null;
4473
+ }
4474
+ return sanitizeRuntimeDiagnosticValue(message);
4475
+ };
4476
+ toSanitizedRuntimeError = (error48) => {
4477
+ const message = getSanitizedRuntimeErrorMessage(error48) || "Unknown runtime error.";
4478
+ if (isRuntimeErrorObject(error48) && error48.message === message) {
4479
+ if (isAbortLikeError(error48) && error48.name !== "AbortError") {
4480
+ if (error48 instanceof Error) error48.name = "AbortError";
4481
+ else return Object.assign(new Error(message), { name: "AbortError" });
4482
+ }
4483
+ return error48;
4484
+ }
4485
+ const sanitized = new Error(message);
4486
+ if (isAbortLikeError(error48)) {
4487
+ sanitized.name = "AbortError";
4488
+ } else if (isRuntimeErrorObject(error48) && error48.name) {
4489
+ sanitized.name = error48.name;
4490
+ }
4491
+ return sanitized;
4492
+ };
4493
+ getSanitizedRuntimeAbortReason = (signal, fallbackMessage = "The operation was aborted.") => isRuntimeErrorObject(signal?.reason) ? toSanitizedRuntimeError(signal.reason) : new DOMException(fallbackMessage, "AbortError");
4494
+ }
4495
+ });
4496
+
4337
4497
  // lib/cli-release/updater.ts
4338
4498
  var updater_exports = {};
4339
4499
  __export(updater_exports, {
@@ -4389,6 +4549,7 @@ var init_updater = __esm({
4389
4549
  init_stop_signals();
4390
4550
  init_config2();
4391
4551
  init_routing();
4552
+ init_runtime_redaction();
4392
4553
  CLI_PACKAGE_NAME = "@vtxmacro/cli";
4393
4554
  OFFICIAL_NPM_REGISTRY = "https://registry.npmjs.org";
4394
4555
  CLI_UPDATE_COMMAND = `npm install -g ${CLI_PACKAGE_NAME}@latest`;
@@ -4423,10 +4584,10 @@ var init_updater = __esm({
4423
4584
  });
4424
4585
  const stdout = [];
4425
4586
  const stderr = [];
4426
- let settled = false;
4587
+ let settled2 = false;
4427
4588
  const settle = (result) => {
4428
- if (settled) return;
4429
- settled = true;
4589
+ if (settled2) return;
4590
+ settled2 = true;
4430
4591
  resolvePromise(result);
4431
4592
  };
4432
4593
  child.stdout.on("data", (chunk) => stdout.push(Buffer.from(chunk)));
@@ -4844,7 +5005,7 @@ var init_updater = __esm({
4844
5005
  try {
4845
5006
  await ensureUpdaterPrivateDirectory(paths.root, paths.root, { platform: input.platform });
4846
5007
  } catch (error48) {
4847
- const reason = `update_directory_unsafe: ${error48 instanceof Error ? error48.message.slice(0, runtime_policy_generated_default.agent_cli.update_failure_reason_max_chars) : "unknown"}`;
5008
+ const reason = `update_directory_unsafe: ${error48 instanceof Error ? sanitizeRuntimeDiagnosticValue(error48.message).slice(0, runtime_policy_generated_default.agent_cli.update_failure_reason_max_chars) : "unknown"}`;
4848
5009
  await appendCliUpdateLog(paths, "cli_update_failed", { package_version: target.version, reason });
4849
5010
  return { kind: "failed", reason };
4850
5011
  }
@@ -4877,7 +5038,7 @@ var init_updater = __esm({
4877
5038
  await appendCliUpdateLog(paths, "cli_release_staged", { package_version: selection.package_version });
4878
5039
  return { kind: "staged", selection };
4879
5040
  } catch (error48) {
4880
- const reason = error48 instanceof Error ? error48.message.slice(0, runtime_policy_generated_default.agent_cli.update_failure_reason_max_chars) : "unknown";
5041
+ const reason = error48 instanceof Error ? sanitizeRuntimeDiagnosticValue(error48.message).slice(0, runtime_policy_generated_default.agent_cli.update_failure_reason_max_chars) : "unknown";
4881
5042
  await appendCliUpdateLog(paths, "cli_update_failed", { package_version: target.version, reason });
4882
5043
  return { kind: "failed", reason };
4883
5044
  } finally {
@@ -4965,7 +5126,7 @@ var init_updater = __esm({
4965
5126
  return runSelected();
4966
5127
  } catch (error48) {
4967
5128
  await appendCliUpdateLog(paths, "cli_update_check_failed", {
4968
- reason: error48 instanceof Error ? error48.message.slice(0, runtime_policy_generated_default.agent_cli.update_failure_reason_max_chars) : "unknown"
5129
+ reason: error48 instanceof Error ? sanitizeRuntimeDiagnosticValue(error48.message).slice(0, runtime_policy_generated_default.agent_cli.update_failure_reason_max_chars) : "unknown"
4969
5130
  });
4970
5131
  return { kind: "run" };
4971
5132
  }
@@ -5393,7 +5554,7 @@ var init_updater = __esm({
5393
5554
  return active && compareCliReleaseVersions(active.package_version, current) > 0 && rejection?.package_version !== active.package_version ? active : null;
5394
5555
  } catch (error48) {
5395
5556
  await appendCliUpdateLog(paths, "cli_runtime_release_poll_failed", {
5396
- reason: error48 instanceof Error ? error48.message.slice(0, runtime_policy_generated_default.agent_cli.update_failure_reason_max_chars) : "unknown"
5557
+ reason: error48 instanceof Error ? sanitizeRuntimeDiagnosticValue(error48.message).slice(0, runtime_policy_generated_default.agent_cli.update_failure_reason_max_chars) : "unknown"
5397
5558
  });
5398
5559
  return null;
5399
5560
  }
@@ -21026,6 +21187,7 @@ var init_runtime_policy_generated2 = __esm({
21026
21187
  runtime: {
21027
21188
  assignment_page_default_limit: 20,
21028
21189
  client_candidate_owner_lease_grace_ms: 6e4,
21190
+ bot_switch_max_retries: 2,
21029
21191
  client_server_heartbeats_per_owner_lease: 2,
21030
21192
  client_server_heartbeat_min_ms: 5e3,
21031
21193
  client_server_heartbeat_max_ms: 3e4
@@ -23616,20 +23778,20 @@ var init_credential_store = __esm({
23616
23778
  stdio: ["pipe", "pipe", "pipe"],
23617
23779
  windowsHide: true
23618
23780
  });
23619
- let settled = false;
23781
+ let settled2 = false;
23620
23782
  let terminating = false;
23621
23783
  const cleanup = () => {
23622
23784
  clearTimeout(timer);
23623
23785
  options.signal?.removeEventListener("abort", abort);
23624
23786
  };
23625
23787
  const settleReject = (error48) => {
23626
- if (settled) return;
23627
- settled = true;
23788
+ if (settled2) return;
23789
+ settled2 = true;
23628
23790
  cleanup();
23629
23791
  reject(error48);
23630
23792
  };
23631
23793
  const terminate = (error48) => {
23632
- if (settled || terminating) return;
23794
+ if (settled2 || terminating) return;
23633
23795
  terminating = true;
23634
23796
  void terminateCredentialProcessTree(child).finally(() => settleReject(error48));
23635
23797
  };
@@ -23652,12 +23814,12 @@ var init_credential_store = __esm({
23652
23814
  child.stderr.resume();
23653
23815
  child.once("error", () => settleReject(new Error("OS credential command could not start.")));
23654
23816
  child.once("close", (exitCode) => {
23655
- if (terminating || settled) return;
23817
+ if (terminating || settled2) return;
23656
23818
  try {
23657
23819
  const normalizedExitCode = Number(exitCode ?? 1);
23658
23820
  const stdout = Buffer.concat(stdoutChunks).toString("utf8");
23659
23821
  const transformedStdout = normalizedExitCode === 0 ? command.transformStdout?.(stdout) ?? stdout : stdout;
23660
- settled = true;
23822
+ settled2 = true;
23661
23823
  cleanup();
23662
23824
  resolve14({
23663
23825
  exitCode: normalizedExitCode,
@@ -24886,16 +25048,16 @@ async function beginInferenceOAuthLogin(options) {
24886
25048
  state: pkce.state,
24887
25049
  challenge: pkce.challenge
24888
25050
  });
24889
- let settled = false;
25051
+ let settled2 = false;
24890
25052
  let rejectCompletion;
24891
25053
  const completion = new Promise((resolve14, reject) => {
24892
25054
  rejectCompletion = reject;
24893
25055
  handler = async (requestUrl2, method, writeResponse) => {
24894
- if (settled) {
25056
+ if (settled2) {
24895
25057
  writeResponse(HTTP_STATUS.CONFLICT, "Authorization callback is no longer active.");
24896
25058
  return;
24897
25059
  }
24898
- settled = true;
25060
+ settled2 = true;
24899
25061
  try {
24900
25062
  if (method !== "GET") throw new Error("Inference OAuth callback is invalid.");
24901
25063
  const callbackUrl = new URL(requestUrl2, redirectUri).toString();
@@ -24980,8 +25142,8 @@ async function beginInferenceOAuthLogin(options) {
24980
25142
  };
24981
25143
  });
24982
25144
  const abortLogin = () => {
24983
- if (settled) return;
24984
- settled = true;
25145
+ if (settled2) return;
25146
+ settled2 = true;
24985
25147
  void closeServer(server).finally(() => rejectCompletion(
24986
25148
  new InferenceOAuthRequestError(
24987
25149
  "request_aborted",
@@ -24992,8 +25154,8 @@ async function beginInferenceOAuthLogin(options) {
24992
25154
  options.signal?.addEventListener("abort", abortLogin, { once: true });
24993
25155
  if (options.signal?.aborted) abortLogin();
24994
25156
  const timeout = setTimeout(() => {
24995
- if (settled) return;
24996
- settled = true;
25157
+ if (settled2) return;
25158
+ settled2 = true;
24997
25159
  void closeServer(server).finally(
24998
25160
  () => rejectCompletion(new Error("Inference OAuth authorization timed out."))
24999
25161
  );
@@ -25014,8 +25176,8 @@ async function beginInferenceOAuthLogin(options) {
25014
25176
  redirectUri,
25015
25177
  completion,
25016
25178
  cancel: async () => {
25017
- if (settled) return;
25018
- settled = true;
25179
+ if (settled2) return;
25180
+ settled2 = true;
25019
25181
  await closeServer(server);
25020
25182
  rejectCompletion(new Error("Inference OAuth authorization was cancelled."));
25021
25183
  }
@@ -25118,6 +25280,7 @@ var init_mcp_client = __esm({
25118
25280
  init_runtime_policy_generated2();
25119
25281
  init_constants();
25120
25282
  init_mcp_transport();
25283
+ init_runtime_redaction();
25121
25284
  init_external_inference_contract();
25122
25285
  EXTERNAL_INFERENCE_MCP_PROTOCOL_VERSION = "2026-07-28";
25123
25286
  EXTERNAL_INFERENCE_AUTOMATED_HOST_TOOLS = [
@@ -25298,7 +25461,7 @@ var init_mcp_client = __esm({
25298
25461
  publicRejectionReason = (text) => {
25299
25462
  const marker = text.indexOf(PUBLIC_TOOL_ERROR_PREFIX);
25300
25463
  const [firstLine = ""] = (marker < 0 ? text : text.slice(0, marker)).split("\n");
25301
- const reason = firstLine.replace(CONTROL_CHARACTERS, " ").trim();
25464
+ const reason = sanitizeRuntimeDiagnosticValue(firstLine.replace(CONTROL_CHARACTERS, " ")).trim();
25302
25465
  if (!reason) return null;
25303
25466
  return reason.length > MAX_REJECTION_REASON_CHARS ? `${reason.slice(0, MAX_REJECTION_REASON_CHARS)}\u2026` : reason;
25304
25467
  };
@@ -35852,7 +36015,7 @@ var init_runner = __esm({
35852
36015
  };
35853
36016
  settlesWithin = async (promise2, timeoutMs) => {
35854
36017
  let timer = null;
35855
- const settled = await Promise.race([
36018
+ const settled2 = await Promise.race([
35856
36019
  promise2.then(() => true, () => true),
35857
36020
  new Promise((resolve14) => {
35858
36021
  timer = setTimeout(
@@ -35862,7 +36025,7 @@ var init_runner = __esm({
35862
36025
  })
35863
36026
  ]);
35864
36027
  if (timer !== null) clearTimeout(timer);
35865
- return settled;
36028
+ return settled2;
35866
36029
  };
35867
36030
  defaultRegisterSignalHandlers = (requestDrain) => {
35868
36031
  const onSigint = () => requestDrain("sigint");
@@ -41323,10 +41486,10 @@ var init_codex_adapter = __esm({
41323
41486
  }
41324
41487
  const start = this.durableSessionStart;
41325
41488
  return await new Promise((resolveSession, reject) => {
41326
- let settled = false;
41489
+ let settled2 = false;
41327
41490
  const finish = (callback) => {
41328
- if (settled) return;
41329
- settled = true;
41491
+ if (settled2) return;
41492
+ settled2 = true;
41330
41493
  clearTimeout(timer);
41331
41494
  signal?.removeEventListener("abort", onAbort);
41332
41495
  callback();
@@ -41402,10 +41565,10 @@ var init_codex_adapter = __esm({
41402
41565
  }
41403
41566
  async waitForCapabilities(preflight, deadlineAtMs, signal) {
41404
41567
  return await new Promise((resolve14, reject) => {
41405
- let settled = false;
41568
+ let settled2 = false;
41406
41569
  const finish = (callback) => {
41407
- if (settled) return;
41408
- settled = true;
41570
+ if (settled2) return;
41571
+ settled2 = true;
41409
41572
  clearTimeout(timer);
41410
41573
  signal?.removeEventListener("abort", onAbort);
41411
41574
  callback();
@@ -47434,6 +47597,7 @@ var init_service = __esm({
47434
47597
  init_define_VTX_GROK_POLICY();
47435
47598
  init_define_VTX_PI_MODEL_POLICY();
47436
47599
  init_service_launcher_state();
47600
+ init_runtime_redaction();
47437
47601
  init_agent_cli_release();
47438
47602
  init_runtime_policy_generated();
47439
47603
  init_constants();
@@ -48720,7 +48884,7 @@ ${result.stderr}`)) {
48720
48884
  event: "worker_output",
48721
48885
  instance_name: worker.instance_name,
48722
48886
  stream,
48723
- message: line.slice(0, SERVICE_POLICY.worker_output_line_max_chars)
48887
+ message: sanitizeRuntimeDiagnosticValue(line).slice(0, SERVICE_POLICY.worker_output_line_max_chars)
48724
48888
  })}
48725
48889
  `);
48726
48890
  }
@@ -49000,8 +49164,8 @@ ${result.stderr}`)) {
49000
49164
  record5.controller.abort();
49001
49165
  await updateRecord(record5, "draining");
49002
49166
  }
49003
- const settled = await Promise.allSettled(retiring.map((record5) => record5.promise));
49004
- const failedDrain = settled.find(
49167
+ const settled2 = await Promise.allSettled(retiring.map((record5) => record5.promise));
49168
+ const failedDrain = settled2.find(
49005
49169
  (result) => result.status === "rejected"
49006
49170
  );
49007
49171
  if (failedDrain) {
@@ -49035,8 +49199,8 @@ ${result.stderr}`)) {
49035
49199
  record5.controller.abort();
49036
49200
  await updateRecord(record5, "draining");
49037
49201
  }
49038
- const settled = await Promise.allSettled(draining.map((record5) => record5.promise));
49039
- const failedDrain = settled.find(
49202
+ const settled2 = await Promise.allSettled(draining.map((record5) => record5.promise));
49203
+ const failedDrain = settled2.find(
49040
49204
  (result) => result.status === "rejected"
49041
49205
  );
49042
49206
  if (failedDrain) throw failedDrain.reason;
@@ -49079,8 +49243,8 @@ ${result.stderr}`)) {
49079
49243
  await drainWorkers();
49080
49244
  break;
49081
49245
  }
49082
- const settled = await completion;
49083
- const failure2 = settled.find((result) => result.status === "rejected");
49246
+ const settled2 = await completion;
49247
+ const failure2 = settled2.find((result) => result.status === "rejected");
49084
49248
  if (failure2) throw failure2.reason;
49085
49249
  break;
49086
49250
  }
@@ -55605,63 +55769,6 @@ var init_request_encoding = __esm({
55605
55769
  }
55606
55770
  });
55607
55771
 
55608
- // lib/runtime/abort.ts
55609
- var ABORT_MESSAGE_TOKENS, readAbortLikeMessage, isAbortLikeError, toAbortError;
55610
- var init_abort = __esm({
55611
- "lib/runtime/abort.ts"() {
55612
- "use strict";
55613
- init_define_VTX_EXO_POLICY();
55614
- init_define_VTX_GROK_POLICY();
55615
- init_define_VTX_PI_MODEL_POLICY();
55616
- ABORT_MESSAGE_TOKENS = [
55617
- "the operation was aborted",
55618
- "the user aborted a request",
55619
- "request was aborted",
55620
- "request aborted",
55621
- "signal is aborted",
55622
- "client runtime stop requested"
55623
- ];
55624
- readAbortLikeMessage = (error48) => {
55625
- if (error48 instanceof Error) {
55626
- return error48.message;
55627
- }
55628
- if (typeof error48 === "string") {
55629
- return error48;
55630
- }
55631
- if (error48 && typeof error48 === "object" && typeof error48.message === "string") {
55632
- return String(error48.message);
55633
- }
55634
- return "";
55635
- };
55636
- isAbortLikeError = (error48) => {
55637
- if (typeof DOMException !== "undefined" && error48 instanceof DOMException) {
55638
- return error48.name === "AbortError";
55639
- }
55640
- if (error48 instanceof Error && error48.name === "AbortError") {
55641
- return true;
55642
- }
55643
- if (error48 && typeof error48 === "object" && error48.name === "AbortError") {
55644
- return true;
55645
- }
55646
- const normalized = readAbortLikeMessage(error48).trim().toLowerCase();
55647
- if (!normalized) {
55648
- return false;
55649
- }
55650
- return ABORT_MESSAGE_TOKENS.some((token) => normalized.includes(token));
55651
- };
55652
- toAbortError = (error48, fallbackMessage = "The operation was aborted.") => {
55653
- const message = readAbortLikeMessage(error48).trim() || fallbackMessage;
55654
- try {
55655
- return new DOMException(message, "AbortError");
55656
- } catch {
55657
- const fallback = new Error(message);
55658
- fallback.name = "AbortError";
55659
- return fallback;
55660
- }
55661
- };
55662
- }
55663
- });
55664
-
55665
55772
  // lib/api/shared.ts
55666
55773
  function configureApiTransport(transport) {
55667
55774
  if (transport === null) {
@@ -55689,7 +55796,7 @@ function getProfileHeaders(baseHeaders = {}, explicitProfileId) {
55689
55796
  if (profileId) headers["x-profile-id"] = profileId.toString();
55690
55797
  return headers;
55691
55798
  }
55692
- var configuredApiTransport, getApiUrl, sendApiRequest, apiFetch, sleep, inFlightClientGetRequests, recentClientGetResponses, clientGetRequestGenerations, initializedClientGetRequestKeys, CLIENT_GET_DEDUPE_TTL_MS, CLIENT_RUNTIME_STATUSES_DEDUPE_TTL_MS, CLIENT_LLM_CONFIG_PRIME_TTL_MS, AUTH_BOOTSTRAP_GET_MAX_ATTEMPTS, AUTH_BOOTSTRAP_RETRY_JITTER_MS, canUseClientGetRequestCache, invalidateClientGetRequestCache, raceWithAbortSignal, shareClientGetRequest, clientGetRequestKey, clientPreferencesRequestKey, invalidateClientPreferencesCache, parseRetryAfterMs2, resolveAuthBootstrapRetryDelayMs, fetchAuthBootstrapGetWithRetry, annotateMarketDataRequestError, buildMarketDataFetchError, buildMarketDataNetworkError, buildMarketDataResponseBodyError, isTransientNetworkFetchError, createIdempotencyKey, getErrorMessage, getErrorPayloadOrEmpty, getErrorPayloadOrFallbackDetail, getErrorMessageFromResponse, throwUnauthorizedIfNeeded, activeProfileId, PROFILE_STORAGE_KEY;
55799
+ var configuredApiTransport, getApiUrl, sendApiRequest, apiFetch, sleep, DEVICE_CLOCK_HEADER, deviceClockHeader, inFlightClientGetRequests, recentClientGetResponses, clientGetRequestGenerations, initializedClientGetRequestKeys, CLIENT_GET_DEDUPE_TTL_MS, CLIENT_RUNTIME_STATUSES_DEDUPE_TTL_MS, CLIENT_LLM_CONFIG_PRIME_TTL_MS, AUTH_BOOTSTRAP_GET_MAX_ATTEMPTS, AUTH_BOOTSTRAP_RETRY_JITTER_MS, canUseClientGetRequestCache, invalidateClientGetRequestCache, raceWithAbortSignal, shareClientGetRequest, clientGetRequestKey, clientPreferencesRequestKey, invalidateClientPreferencesCache, parseRetryAfterMs2, resolveAuthBootstrapRetryDelayMs, fetchAuthBootstrapGetWithRetry, annotateMarketDataRequestError, buildMarketDataFetchError, buildMarketDataNetworkError, buildMarketDataResponseBodyError, isTransientNetworkFetchError, createIdempotencyKey, getErrorMessage, getErrorPayloadOrEmpty, getErrorPayloadOrFallbackDetail, getErrorMessageFromResponse, throwUnauthorizedIfNeeded, activeProfileId, PROFILE_STORAGE_KEY;
55693
55800
  var init_shared = __esm({
55694
55801
  "lib/api/shared.ts"() {
55695
55802
  "use strict";
@@ -55702,6 +55809,7 @@ var init_shared = __esm({
55702
55809
  init_runtime_policy_generated2();
55703
55810
  init_constants();
55704
55811
  init_abort();
55812
+ init_runtime_redaction();
55705
55813
  configuredApiTransport = null;
55706
55814
  getApiUrl = () => {
55707
55815
  if (configuredApiTransport) return configuredApiTransport.baseUrl;
@@ -55736,6 +55844,8 @@ var init_shared = __esm({
55736
55844
  return sent !== init2 && refusedUnread(response, readsGzip) ? sendApiRequest(input, init2) : response;
55737
55845
  };
55738
55846
  sleep = (ms) => new Promise((resolve14) => setTimeout(resolve14, ms));
55847
+ DEVICE_CLOCK_HEADER = "X-Device-Clock-Ms";
55848
+ deviceClockHeader = () => ({ [DEVICE_CLOCK_HEADER]: String(Date.now()) });
55739
55849
  inFlightClientGetRequests = /* @__PURE__ */ new Map();
55740
55850
  recentClientGetResponses = /* @__PURE__ */ new Map();
55741
55851
  clientGetRequestGenerations = /* @__PURE__ */ new Map();
@@ -55850,7 +55960,7 @@ var init_shared = __esm({
55850
55960
  responseText = "";
55851
55961
  }
55852
55962
  const statusText = response.statusText ? ` ${response.statusText}` : "";
55853
- const detail = responseText ? `: ${responseText.slice(0, runtime_policy_generated_default2.ui.api_client.market_data_error_detail_chars)}` : "";
55963
+ const detail = responseText ? `: ${sanitizeRuntimeDiagnosticValue(responseText).slice(0, runtime_policy_generated_default2.ui.api_client.market_data_error_detail_chars)}` : "";
55854
55964
  return annotateMarketDataRequestError(
55855
55965
  new Error(`Market data request failed: ${label2} unavailable (HTTP ${response.status}${statusText})${detail}`),
55856
55966
  path,
@@ -56322,68 +56432,6 @@ var init_google_auth_url = __esm({
56322
56432
  }
56323
56433
  });
56324
56434
 
56325
- // lib/runtime/runtime-redaction.ts
56326
- var REDACTED_VALUE, SECRET_QUERY_PARAM_PATTERN, BEARER_TOKEN_PATTERN, SECRET_ASSIGNMENT_PATTERN, SECRET_KEYWORD_VALUE_PATTERN, OPENAI_STYLE_KEY_PATTERN, VERTEX_EXPRESS_KEY_PATTERN, isRuntimeErrorObject, sanitizeRuntimeDiagnosticValue, sanitizeRuntimeNetworkPath, getSanitizedRuntimeErrorMessage, toSanitizedRuntimeError, getSanitizedRuntimeAbortReason;
56327
- var init_runtime_redaction = __esm({
56328
- "lib/runtime/runtime-redaction.ts"() {
56329
- "use strict";
56330
- init_define_VTX_EXO_POLICY();
56331
- init_define_VTX_GROK_POLICY();
56332
- init_define_VTX_PI_MODEL_POLICY();
56333
- init_abort();
56334
- REDACTED_VALUE = "[REDACTED]";
56335
- SECRET_QUERY_PARAM_PATTERN = /([?&](?:access_token|api(?:_|-)?key|auth|authorization|key|private_key|secret|sig|signature|token)=)[^&#\s]*/gi;
56336
- BEARER_TOKEN_PATTERN = /\b(Bearer)\s+[A-Za-z0-9._:-]+\b/gi;
56337
- SECRET_ASSIGNMENT_PATTERN = /((?:authorization\s*[:=]\s*['"]?Bearer\s+|x-api-key\s*[:=]\s*['"]?|api(?:_|-)?key\s*[:=]\s*['"]?|\bkey\s*[:=]\s*['"]?|token\s*[:=]\s*['"]?|secret\s*[:=]\s*['"]?))[^'"\s,}]+/gi;
56338
- SECRET_KEYWORD_VALUE_PATTERN = /((?:private(?:_|-|\s)?key|signing(?:_|-|\s)?key)\s*[:=]\s*['"]?)(0x[a-fA-F0-9]{64}|[^'"\s,}]+)/gi;
56339
- OPENAI_STYLE_KEY_PATTERN = /\bsk-[A-Za-z0-9._-]+\b/g;
56340
- VERTEX_EXPRESS_KEY_PATTERN = /\bAQ\.[A-Za-z0-9._-]+\b/g;
56341
- isRuntimeErrorObject = (error48) => error48 instanceof Error || error48 != null && typeof error48 === "object" && Object.prototype.toString.call(error48) === "[object DOMException]" && typeof error48.message === "string" && typeof error48.name === "string";
56342
- sanitizeRuntimeDiagnosticValue = (value) => {
56343
- const normalized = String(value || "");
56344
- if (!normalized) {
56345
- return normalized;
56346
- }
56347
- return normalized.replace(SECRET_QUERY_PARAM_PATTERN, `$1${REDACTED_VALUE}`).replace(BEARER_TOKEN_PATTERN, `$1 ${REDACTED_VALUE}`).replace(SECRET_ASSIGNMENT_PATTERN, `$1${REDACTED_VALUE}`).replace(SECRET_KEYWORD_VALUE_PATTERN, `$1${REDACTED_VALUE}`).replace(OPENAI_STYLE_KEY_PATTERN, REDACTED_VALUE).replace(VERTEX_EXPRESS_KEY_PATTERN, REDACTED_VALUE);
56348
- };
56349
- sanitizeRuntimeNetworkPath = (value) => {
56350
- const normalized = String(value || "").trim();
56351
- if (!normalized) {
56352
- return "/";
56353
- }
56354
- const withoutFragment = normalized.split("#", 1)[0] || normalized;
56355
- const withoutQuery = withoutFragment.split("?", 1)[0] || withoutFragment;
56356
- const sanitized = sanitizeRuntimeDiagnosticValue(withoutQuery.trim());
56357
- return sanitized || "/";
56358
- };
56359
- getSanitizedRuntimeErrorMessage = (error48) => {
56360
- const message = isRuntimeErrorObject(error48) ? error48.message : typeof error48 === "string" ? error48 : error48 == null ? null : String(error48);
56361
- if (message == null) {
56362
- return null;
56363
- }
56364
- return sanitizeRuntimeDiagnosticValue(message);
56365
- };
56366
- toSanitizedRuntimeError = (error48) => {
56367
- const message = getSanitizedRuntimeErrorMessage(error48) || "Unknown runtime error.";
56368
- if (isRuntimeErrorObject(error48) && error48.message === message) {
56369
- if (isAbortLikeError(error48) && error48.name !== "AbortError") {
56370
- if (error48 instanceof Error) error48.name = "AbortError";
56371
- else return Object.assign(new Error(message), { name: "AbortError" });
56372
- }
56373
- return error48;
56374
- }
56375
- const sanitized = new Error(message);
56376
- if (isAbortLikeError(error48)) {
56377
- sanitized.name = "AbortError";
56378
- } else if (isRuntimeErrorObject(error48) && error48.name) {
56379
- sanitized.name = error48.name;
56380
- }
56381
- return sanitized;
56382
- };
56383
- getSanitizedRuntimeAbortReason = (signal, fallbackMessage = "The operation was aborted.") => isRuntimeErrorObject(signal?.reason) ? toSanitizedRuntimeError(signal.reason) : new DOMException(fallbackMessage, "AbortError");
56384
- }
56385
- });
56386
-
56387
56435
  // lib/runtime/channel-sender.ts
56388
56436
  var RUNTIME_TAB_ID_STORAGE_KEY, createRuntimeUuid, getOrCreateRuntimeTabSenderId;
56389
56437
  var init_channel_sender = __esm({
@@ -57084,6 +57132,7 @@ var init_local_breadcrumbs = __esm({
57084
57132
  init_define_VTX_PI_MODEL_POLICY();
57085
57133
  init_constants();
57086
57134
  init_runtime_policy_generated2();
57135
+ init_runtime_redaction();
57087
57136
  LOCAL_RUNTIME_BREADCRUMBS_STORAGE_KEY = "vtx_client_runtime_local_breadcrumbs_v1";
57088
57137
  DEVICE_DIAGNOSTICS2 = runtime_policy_generated_default2.trading.engine.client_runtime.device_diagnostics;
57089
57138
  LOCAL_RUNTIME_BREADCRUMBS_MAX_ENTRIES = DEVICE_DIAGNOSTICS2.breadcrumbs_max_entries;
@@ -57096,7 +57145,7 @@ var init_local_breadcrumbs = __esm({
57096
57145
  return window;
57097
57146
  };
57098
57147
  sanitizeText = (value, maxLength) => {
57099
- const text = String(value ?? "").trim();
57148
+ const text = sanitizeRuntimeDiagnosticValue(String(value ?? "")).trim();
57100
57149
  if (!text) {
57101
57150
  return null;
57102
57151
  }
@@ -57527,6 +57576,7 @@ var init_market_data = __esm({
57527
57576
  init_define_VTX_GROK_POLICY();
57528
57577
  init_define_VTX_PI_MODEL_POLICY();
57529
57578
  init_abort();
57579
+ init_runtime_redaction();
57530
57580
  init_network_debug();
57531
57581
  init_shared();
57532
57582
  init_constants();
@@ -57837,6 +57887,7 @@ async function getLLMConfig(cookie, profileId, signal) {
57837
57887
  method: "GET",
57838
57888
  headers,
57839
57889
  credentials: "include",
57890
+ cache: "no-store",
57840
57891
  signal: requestSignal
57841
57892
  });
57842
57893
  if (held && response.status === HTTP_STATUS.NOT_MODIFIED) return JSON.parse(held.text);
@@ -57961,6 +58012,17 @@ var init_account_summary = __esm({
57961
58012
  }
57962
58013
  });
57963
58014
 
58015
+ // lib/api/mobile-notifications.ts
58016
+ var init_mobile_notifications = __esm({
58017
+ "lib/api/mobile-notifications.ts"() {
58018
+ "use strict";
58019
+ init_define_VTX_EXO_POLICY();
58020
+ init_define_VTX_GROK_POLICY();
58021
+ init_define_VTX_PI_MODEL_POLICY();
58022
+ init_shared();
58023
+ }
58024
+ });
58025
+
57964
58026
  // lib/runtime/hyperliquid-account-mode-contract.ts
57965
58027
  function resolveExactHyperliquidAccountMode(userAbstraction, ...dexEvidence) {
57966
58028
  const mode = extractCanonicalHyperliquidAccountMode(userAbstraction);
@@ -58958,7 +59020,7 @@ var init_hyperliquid_public_read = __esm({
58958
59020
  let permit = null;
58959
59021
  const rowWeightedReservationId = !hostTransport && HYPERLIQUID_ROW_WEIGHTED_INFO_REQUESTS.includes(requestType) ? crypto.randomUUID() : void 0;
58960
59022
  let outcome = "cancelled";
58961
- let settled;
59023
+ let settled2;
58962
59024
  let acquiring = false;
58963
59025
  let observedRateLimit;
58964
59026
  let privateRouteUsed = false;
@@ -59002,7 +59064,7 @@ var init_hyperliquid_public_read = __esm({
59002
59064
  checkAbort(signal);
59003
59065
  }
59004
59066
  pending2.set(key, { promise: new Promise((resolve14) => {
59005
- settled = resolve14;
59067
+ settled2 = resolve14;
59006
59068
  }), priority });
59007
59069
  }
59008
59070
  if (options.reservation?.closed) throw new DOMException("Hyperliquid account read was cancelled.", "AbortError");
@@ -59115,9 +59177,9 @@ var init_hyperliquid_public_read = __esm({
59115
59177
  try {
59116
59178
  await finishHyperliquidRecoveryRequest(permit, outcome);
59117
59179
  } finally {
59118
- if (settled) {
59180
+ if (settled2) {
59119
59181
  pending2.delete(key);
59120
- settled();
59182
+ settled2();
59121
59183
  }
59122
59184
  }
59123
59185
  }
@@ -59882,7 +59944,7 @@ var init_error_surface_contract = __esm({
59882
59944
  return `${pausePrefix}: Critical behavior context could not be constructed for this cycle. The cycle was skipped safely; VTX will retry at the next scheduled cycle.`;
59883
59945
  }
59884
59946
  if (classificationBasis.includes("critical behavior state is unavailable for this trading cycle")) {
59885
- return `${pausePrefix}: Your prompt on the AI page contains something VTX can't use, for example copied DATA FORMAT definitions in the System Prompt. Fix the prompt; VTX skipped this cycle and will retry at the next scheduled cycle.`;
59947
+ return `${pausePrefix}: Your prompt on the AI page contains something VTX can't use, for example a <behavior_state> line in the System Prompt that doesn't start with "- ". Fix the prompt; VTX skipped this cycle and will retry at the next scheduled cycle.`;
59886
59948
  }
59887
59949
  if (classificationBasis.includes(
59888
59950
  "client runtime decision persistence deadline exceeded after the ai run completed"
@@ -91657,7 +91719,12 @@ var init_hyperliquid_client = __esm({
91657
91719
  };
91658
91720
  fetchBrowserAccountState = async (input) => {
91659
91721
  const user = requireWalletAddress(input.walletAddress);
91660
- const payload = await postHyperliquidInfo(input, { type: "clearinghouseState", user }, "hyperliquid.clearinghouseState");
91722
+ const dex = String(input.dex ?? "").trim().toLowerCase();
91723
+ const payload = await postHyperliquidInfo(
91724
+ input,
91725
+ { type: "clearinghouseState", user, ...dex ? { dex } : {} },
91726
+ "hyperliquid.clearinghouseState"
91727
+ );
91661
91728
  if (!payload || typeof payload !== "object" || Array.isArray(payload)) {
91662
91729
  throw new Error("Malformed Hyperliquid clearinghouseState response.");
91663
91730
  }
@@ -91675,8 +91742,10 @@ var init_hyperliquid_client = __esm({
91675
91742
  const positions = Array.isArray(state2.assetPositions) ? state2.assetPositions.map((entry) => {
91676
91743
  const assetPosition = entry;
91677
91744
  const position = assetPosition.position || {};
91745
+ const coin = String(position.coin || assetPosition.coin || "");
91678
91746
  return {
91679
- symbol: String(position.coin || assetPosition.coin || ""),
91747
+ // A HIP-3 DEX may name its coins without the DEX.
91748
+ symbol: dex && coin && !coin.includes(":") ? `${dex}:${coin}` : coin,
91680
91749
  size: toFiniteNumber(position.szi, 0),
91681
91750
  entry_price: position.entryPx == null ? null : toFiniteNumber(position.entryPx, 0),
91682
91751
  unrealized_pnl: position.unrealizedPnl == null ? null : toFiniteNumber(position.unrealizedPnl, 0),
@@ -91706,7 +91775,7 @@ var init_hyperliquid_client = __esm({
91706
91775
  };
91707
91776
  fetchBrowserPosition = async (input) => {
91708
91777
  const symbol2 = normalizeSymbol(input.symbol);
91709
- const accountState = await fetchBrowserAccountState(input);
91778
+ const accountState = await fetchBrowserAccountState({ ...input, dex: getHyperliquidMarketDex(symbol2) });
91710
91779
  return accountState.positions.find((position) => normalizeSymbol(position.symbol) === symbol2) ?? null;
91711
91780
  };
91712
91781
  buildHyperliquidOrderWire = async (input, tif, price, priceKind) => {
@@ -92762,7 +92831,7 @@ var init_hyperliquid_client = __esm({
92762
92831
  }
92763
92832
  settlementAttempted = true;
92764
92833
  try {
92765
- const settled = await settleClientRuntimeExchangeMutation(
92834
+ const settled2 = await settleClientRuntimeExchangeMutation(
92766
92835
  durableMutation.profileId,
92767
92836
  durableMutation.mutationId,
92768
92837
  {
@@ -92777,10 +92846,10 @@ var init_hyperliquid_client = __esm({
92777
92846
  ...durableMutationAuthorityArgs(durableMutation)
92778
92847
  );
92779
92848
  try {
92780
- durableMutation.onSettled?.(settled);
92849
+ durableMutation.onSettled?.(settled2);
92781
92850
  } catch {
92782
92851
  }
92783
- return settled;
92852
+ return settled2;
92784
92853
  } catch (settlementCause) {
92785
92854
  throw Object.assign(new RuntimeExecutionError(
92786
92855
  "Exchange submission may have completed; durable reconciliation is pending.",
@@ -92825,10 +92894,10 @@ var init_hyperliquid_client = __esm({
92825
92894
  );
92826
92895
  }
92827
92896
  await new Promise((resolve14) => {
92828
- let settled = false;
92897
+ let settled2 = false;
92829
92898
  const finish = () => {
92830
- if (settled) return;
92831
- settled = true;
92899
+ if (settled2) return;
92900
+ settled2 = true;
92832
92901
  globalThis.clearTimeout(timeoutId);
92833
92902
  input.signal?.removeEventListener("abort", finish);
92834
92903
  resolve14();
@@ -93579,7 +93648,8 @@ async function postClientRuntime(path, profileId, body, options) {
93579
93648
  signal: requestSignal,
93580
93649
  headers: {
93581
93650
  ...requestHeaders,
93582
- ...lastRequestId ? { "X-Request-ID": lastRequestId } : {}
93651
+ ...lastRequestId ? { "X-Request-ID": lastRequestId } : {},
93652
+ ...deviceClockHeader()
93583
93653
  },
93584
93654
  body
93585
93655
  });
@@ -94701,6 +94771,7 @@ var init_api2 = __esm({
94701
94771
  init_bot_exchanges();
94702
94772
  init_local_breadcrumbs();
94703
94773
  init_abort();
94774
+ init_runtime_redaction();
94704
94775
  init_client_runtime_ownership_errors();
94705
94776
  init_shared();
94706
94777
  init_shared();
@@ -94716,6 +94787,7 @@ var init_api2 = __esm({
94716
94787
  init_updates();
94717
94788
  init_profile_emoji();
94718
94789
  init_account_summary();
94790
+ init_mobile_notifications();
94719
94791
  init_server_runtime_lease();
94720
94792
  clientRuntimeSecretHeaders = (profileId) => {
94721
94793
  const headers = getProfileHeaders({}, profileId);
@@ -94799,9 +94871,8 @@ var init_api2 = __esm({
94799
94871
  if ("invocations" in payload) {
94800
94872
  body.invocations = payload.invocations ?? [];
94801
94873
  }
94802
- if (payload.stopReason !== void 0) {
94803
- body.stop_reason = payload.stopReason ?? null;
94804
- }
94874
+ if (payload.stopReason !== void 0) body.stop_reason = payload.stopReason ?? null;
94875
+ if (payload.modeSwitch) body.mode_switch = true;
94805
94876
  if (payload.authoritativeIntent !== void 0) {
94806
94877
  body.authoritative_intent = payload.authoritativeIntent;
94807
94878
  }
@@ -95256,7 +95327,7 @@ var init_api2 = __esm({
95256
95327
  if (code !== "client_exchange_evidence_invalid") throw error48;
95257
95328
  appendRuntimeDebugEvent({
95258
95329
  label: "client_exchange_reconcile_evidence_rejected",
95259
- note: `mutation_id=${answer.mutation_id} code=${code} detail=${String(error48.message ?? "").slice(0, runtime_policy_generated_default2.ui.api_client.exchange_evidence_rejection_detail_chars)}`,
95330
+ note: `mutation_id=${answer.mutation_id} code=${code} detail=${sanitizeRuntimeDiagnosticValue(String(error48.message ?? "")).slice(0, runtime_policy_generated_default2.ui.api_client.exchange_evidence_rejection_detail_chars)}`,
95260
95331
  outcome: "error"
95261
95332
  });
95262
95333
  return answer;
@@ -95994,6 +96065,7 @@ var init_vault = __esm({
95994
96065
  init_define_VTX_GROK_POLICY();
95995
96066
  init_define_VTX_PI_MODEL_POLICY();
95996
96067
  init_host_storage();
96068
+ init_runtime_redaction();
95997
96069
  init_api2();
95998
96070
  init_client_runtime_secret_contract();
95999
96071
  init_client_runtime_provider_contract();
@@ -97783,8 +97855,8 @@ var init_hyperliquid_account_state_adapter = __esm({
97783
97855
  return await Promise.all(reads);
97784
97856
  } catch (error48) {
97785
97857
  controller.abort(error48);
97786
- const settled = await Promise.allSettled(reads);
97787
- for (const result of settled) {
97858
+ const settled2 = await Promise.allSettled(reads);
97859
+ for (const result of settled2) {
97788
97860
  if (result.status === "rejected" && result.reason instanceof HyperliquidPublicReadError && result.reason.code === "public_rate_limited") throw result.reason;
97789
97861
  }
97790
97862
  throw error48;
@@ -98688,7 +98760,7 @@ var init_protective_evidence = __esm({
98688
98760
  });
98689
98761
 
98690
98762
  // lib/runtime/protective-actions.ts
98691
- var DECIMAL, CLOID, fail2, exactKeys, nonNegativeInteger, decimalString, POSITION_ORDER_SIZE, orderSizeString, canonicalTriggerOrder, canonicalProtectiveWireAction, assertProtectiveActionLocallySafe, authorityArgs2, errorCode2, foreignClaimExpiresAtMs, drainLocks, refusedUntil, drainClientProtectiveActions, drainOnce;
98763
+ var DECIMAL, PERCENT, CLOID, fail2, exactKeys, nonNegativeInteger, decimalString, POSITION_ORDER_SIZE, orderSizeString, canonicalTriggerOrder, canonicalProtectiveWireAction, assertProtectiveActionLocallySafe, authorityArgs2, errorCode2, foreignClaimExpiresAtMs, drainLocks, refusedUntil, drainClientProtectiveActions, drainOnce;
98692
98764
  var init_protective_actions = __esm({
98693
98765
  "lib/runtime/protective-actions.ts"() {
98694
98766
  "use strict";
@@ -98705,6 +98777,7 @@ var init_protective_actions = __esm({
98705
98777
  init_error_surface_contract();
98706
98778
  init_protective_evidence();
98707
98779
  DECIMAL = /^(?:0|[1-9]\d*)(?:\.\d+)?$/;
98780
+ PERCENT = /^(?:0|[1-9]\d*)(?:\.\d+)?%$/;
98708
98781
  CLOID = /^0x[0-9a-f]{32}$/;
98709
98782
  fail2 = (message) => {
98710
98783
  throw new RuntimeExecutionError(
@@ -98783,9 +98856,48 @@ var init_protective_actions = __esm({
98783
98856
  if (oid <= 0) fail2("cancel target is invalid.");
98784
98857
  return { type: "cancel", cancels: [{ a: nonNegativeInteger(cancel.a, "asset"), o: oid }] };
98785
98858
  }
98859
+ if (kind === "trailingStop") {
98860
+ const action = exactKeys(wire, ["type", "asset", "isBuy", "sz", "reduceOnly", "retracement", "activationPx"], "action");
98861
+ if (action.reduceOnly !== true) fail2("a trailing stop must be reduce-only.");
98862
+ if (typeof action.isBuy !== "boolean") fail2("trailing stop side is invalid.");
98863
+ if (action.activationPx !== null) fail2("a trailing stop is active at once.");
98864
+ const distance = action.retracement;
98865
+ let retracement;
98866
+ if (distance && typeof distance === "object" && "pct" in distance) {
98867
+ const pct = exactKeys(distance, ["pct"], "retracement").pct;
98868
+ const decimals = typeof pct === "string" && pct.includes(".") ? pct.slice(pct.indexOf(".") + 1, -1).length : 0;
98869
+ if (typeof pct !== "string" || !PERCENT.test(pct) || !(Number(pct.slice(0, -1)) > 0) || decimals > HYPERLIQUID_EXCHANGE_SPECIFICATION.trailing_retracement_pct_max_decimals) {
98870
+ fail2("trailing stop percent is invalid.");
98871
+ }
98872
+ retracement = { pct };
98873
+ } else {
98874
+ retracement = { px: decimalString(exactKeys(distance, ["px"], "retracement").px, "trailing stop distance") };
98875
+ }
98876
+ return {
98877
+ type: "trailingStop",
98878
+ asset: nonNegativeInteger(action.asset, "asset"),
98879
+ isBuy: action.isBuy,
98880
+ sz: decimalString(action.sz, "trailing stop size"),
98881
+ reduceOnly: true,
98882
+ retracement,
98883
+ activationPx: null
98884
+ };
98885
+ }
98786
98886
  return fail2("unsupported action type.");
98787
98887
  };
98788
98888
  assertProtectiveActionLocallySafe = (action, canonical, livePositionSize) => {
98889
+ if (canonical.type === "trailingStop" !== (action.operation_kind === "trailing_stop")) {
98890
+ fail2("operation kind does not match the action.");
98891
+ }
98892
+ if (canonical.type === "trailingStop") {
98893
+ if (action.action_kind !== "place" || action.client_order_ids.length > 0) fail2("trailing stop metadata does not match.");
98894
+ if (canonical.asset !== action.exchange_asset_id) fail2("asset does not match the symbol.");
98895
+ if (livePositionSize == null || !Number.isFinite(livePositionSize) || livePositionSize === 0) {
98896
+ fail2("the live position is flat or unknown.");
98897
+ }
98898
+ if (canonical.isBuy !== livePositionSize < 0) fail2("the trailing stop would not close the live position.");
98899
+ return;
98900
+ }
98789
98901
  const assets = canonical.type === "cancel" ? canonical.cancels.map((cancel) => cancel.a) : canonical.type === "modify" ? [canonical.order.a] : canonical.orders.map((order) => order.a);
98790
98902
  if (assets.some((asset) => asset !== action.exchange_asset_id)) fail2("asset does not match the symbol.");
98791
98903
  if (canonical.type === "cancel") {
@@ -98981,7 +99093,7 @@ var init_protective_actions = __esm({
98981
99093
  });
98982
99094
  continue;
98983
99095
  }
98984
- let settled = null;
99096
+ let settled2 = null;
98985
99097
  try {
98986
99098
  await executeClientPreparedProtectiveAction({
98987
99099
  profileId: input.profileId,
@@ -99000,7 +99112,7 @@ var init_protective_actions = __esm({
99000
99112
  clientOrderIds: action.client_order_ids,
99001
99113
  wireAction: canonical,
99002
99114
  onSettled: (mutation) => {
99003
- settled = mutation;
99115
+ settled2 = mutation;
99004
99116
  }
99005
99117
  });
99006
99118
  result.processed.push({ actionId: action.action_id, actionKind: action.action_kind, outcome: "sent" });
@@ -99012,7 +99124,7 @@ var init_protective_actions = __esm({
99012
99124
  reason: errorCode2(error48) || (error48 instanceof RuntimeExecutionError ? error48.reasonCode : "execution_failed")
99013
99125
  });
99014
99126
  }
99015
- const settledMutation = settled;
99127
+ const settledMutation = settled2;
99016
99128
  if (settledMutation?.protection) result.protection = settledMutation.protection;
99017
99129
  if (settledMutation && Array.isArray(settledMutation.protective_actions)) {
99018
99130
  actions = settledMutation.protective_actions;
@@ -99154,7 +99266,7 @@ var init_client_exchange_mutations = __esm({
99154
99266
  });
99155
99267
 
99156
99268
  // lib/runtime/execution-guard-contract.ts
99157
- var unitsFromPosition, signedUnitsFromPosition, signedUnitsFromEntryPosition, classifyExecutionIntent, reductionFirstOrder, usdAmount, orderMetadataRetryReason, orderCeilingRefusal, resolveExecutionTarget, decisionOrderSizeAsset, flipExecutionLegs, executedOrderPositionEvent;
99269
+ var unitsFromPosition, signedUnitsFromPosition, signedUnitsFromEntryPosition, classifyExecutionIntent, reductionFirstOrder, usdAmount, orderMetadataRetryReason, orderCeilingRefusal, copyClosingSize, copyOrderClosingSize, copyOrderNotionalCap, resolveExecutionTarget, decisionOrderSizeAsset, flipExecutionLegs, executedOrderPositionEvent;
99158
99270
  var init_execution_guard_contract = __esm({
99159
99271
  "lib/runtime/execution-guard-contract.ts"() {
99160
99272
  "use strict";
@@ -99365,6 +99477,10 @@ var init_execution_guard_contract = __esm({
99365
99477
  return null;
99366
99478
  };
99367
99479
  orderCeilingRefusal = (input) => {
99480
+ const closingSide2 = input.side === "sell" && input.currentPositionSize > 0 || input.side === "buy" && input.currentPositionSize < 0;
99481
+ if (input.reduceOnly && closingSide2 && input.size <= Math.abs(input.currentPositionSize)) {
99482
+ return null;
99483
+ }
99368
99484
  const orderNotional = input.size * input.price;
99369
99485
  if (orderNotional > input.maxOrderNotional) {
99370
99486
  return `Order notional ${usdAmount(orderNotional)} exceeds limit ${usdAmount(input.maxOrderNotional)}`;
@@ -99376,6 +99492,23 @@ var init_execution_guard_contract = __esm({
99376
99492
  }
99377
99493
  return null;
99378
99494
  };
99495
+ copyClosingSize = (destinationPosition, destinationDelta) => destinationPosition * destinationDelta >= 0 ? 0 : Math.min(Math.abs(destinationDelta), Math.abs(destinationPosition));
99496
+ copyOrderClosingSize = (input) => {
99497
+ const size = Number.isFinite(input.size) && input.size > 0 ? input.size : 0;
99498
+ if (input.reduceOnly) return size;
99499
+ if (input.actualPosition === null || !Number.isFinite(input.actualPosition)) return 0;
99500
+ const signedSize = String(input.side).trim().toLowerCase() === "buy" ? size : -size;
99501
+ return copyClosingSize(input.actualPosition, signedSize);
99502
+ };
99503
+ copyOrderNotionalCap = (followerCap, platformCap, closingNotional) => {
99504
+ const platform = Number(platformCap);
99505
+ if (!Number.isFinite(platform) || platform <= 0) return null;
99506
+ const closing = Number(closingNotional);
99507
+ const platformBound = (Number.isFinite(closing) && closing > 0 ? closing : 0) + platform;
99508
+ const follower = Number(followerCap);
99509
+ if (!Number.isFinite(follower) || follower <= 0) return platformBound;
99510
+ return Math.min(follower, platformBound);
99511
+ };
99379
99512
  resolveExecutionTarget = (classified, liveSignedUnits, livePositionDirection) => {
99380
99513
  const liveUnits = Number.isFinite(liveSignedUnits) ? Math.trunc(liveSignedUnits) : 0;
99381
99514
  const exactLiveDirection = livePositionDirection == null ? liveUnits > 0 ? 1 : liveUnits < 0 ? -1 : 0 : livePositionDirection;
@@ -99695,7 +99828,7 @@ var init_protective_trigger_price = __esm({
99695
99828
  });
99696
99829
 
99697
99830
  // lib/runtime/protective-stop-replacement.ts
99698
- var STOP_REPLACED, STOP_REPLACEMENT_EXHAUSTED, STOP_REPLACEMENT_REJECTED, STOP_REPLACEMENT_NOT_LANDED, STOP_CLEANUP_IN_FLIGHT, TERMINAL_WITHOUT_FILL, CANCELLED_BY_USER, POSITION_FLAT_AFTER_TERMINAL, CAPACITY_ALREADY_ALLOCATED, TRIGGER_INVALID, STOP_EXECUTION_REJECTED, STOP_TRIGGER_CROSSED, permanentStopRejectionStatuses, protectiveStopRejectionIsPermanent, POSITION_ENDED_ORDER_STATUSES, finiteOrNull, floorToLot, positiveSafeInteger, decimalOrNull, positionTolerance, chainFillChronology, protectivePositionEpisodeEnded, decideProtectiveStopReplacement;
99831
+ var STOP_REPLACED, STOP_REPLACEMENT_EXHAUSTED, STOP_REPLACEMENT_REJECTED, STOP_REPLACEMENT_NOT_LANDED, STOP_CLEANUP_IN_FLIGHT, TERMINAL_WITHOUT_FILL, CANCELLED_BY_USER, POSITION_FLAT_AFTER_TERMINAL, CAPACITY_ALREADY_ALLOCATED, TRIGGER_INVALID, STOP_EXECUTION_REJECTED, STOP_TRIGGER_CROSSED, permanentStopRejectionStatuses, protectiveStopRejectionIsPermanent, POSITION_ENDED_ORDER_STATUSES, finiteOrNull, floorToLot, positiveSafeInteger, decimalOrNull, positionTolerance, chainFillChronology, marketFillChain, noExposureOnSide, protectivePositionEpisodeEnded, decideProtectiveStopReplacement;
99699
99832
  var init_protective_stop_replacement = __esm({
99700
99833
  "lib/runtime/protective-stop-replacement.ts"() {
99701
99834
  "use strict";
@@ -99772,16 +99905,13 @@ var init_protective_stop_replacement = __esm({
99772
99905
  }
99773
99906
  return ordered;
99774
99907
  };
99775
- protectivePositionEpisodeEnded = (input) => {
99776
- if (!POSITION_ENDED_ORDER_STATUSES.has(String(input.orderStatus ?? ""))) return false;
99777
- const statusMs = positiveSafeInteger(input.statusTimestampMs);
99778
- if (statusMs == null || !Array.isArray(input.fills)) return false;
99779
- const market = normalizeHyperliquidMarketSymbol(input.symbol);
99780
- const sign = input.isLong ? 1 : -1;
99908
+ marketFillChain = (fills, symbol2) => {
99909
+ if (!Array.isArray(fills)) return null;
99910
+ const market = normalizeHyperliquidMarketSymbol(symbol2);
99781
99911
  const rows = [];
99782
99912
  const seen = /* @__PURE__ */ new Set();
99783
- for (const fill of input.fills) {
99784
- if (fill == null || typeof fill !== "object" || Array.isArray(fill)) return false;
99913
+ for (const fill of fills) {
99914
+ if (fill == null || typeof fill !== "object" || Array.isArray(fill)) return null;
99785
99915
  const record5 = fill;
99786
99916
  if (normalizeHyperliquidMarketSymbol(String(record5.coin ?? "")) !== market) continue;
99787
99917
  const tradeId = positiveSafeInteger(record5.tid);
@@ -99789,12 +99919,26 @@ var init_protective_stop_replacement = __esm({
99789
99919
  const size = decimalOrNull(record5.sz);
99790
99920
  const start = decimalOrNull(record5.startPosition);
99791
99921
  if (tradeId == null || seen.has(tradeId) || time3 == null || record5.side !== "B" && record5.side !== "A" || size == null || size <= 0 || start == null) {
99792
- return false;
99922
+ return null;
99793
99923
  }
99794
99924
  seen.add(tradeId);
99795
- rows.push({ time: time3, tradeId, start, end: start + (record5.side === "B" ? size : -size) });
99925
+ rows.push({
99926
+ time: time3,
99927
+ tradeId,
99928
+ start,
99929
+ end: start + (record5.side === "B" ? size : -size),
99930
+ orderId: String(record5.oid ?? "").trim()
99931
+ });
99796
99932
  }
99797
- const chained = chainFillChronology(rows);
99933
+ return chainFillChronology(rows);
99934
+ };
99935
+ noExposureOnSide = (position, isLong) => (isLong ? 1 : -1) * position <= positionTolerance(position, 0);
99936
+ protectivePositionEpisodeEnded = (input) => {
99937
+ if (!POSITION_ENDED_ORDER_STATUSES.has(String(input.orderStatus ?? ""))) return false;
99938
+ const statusMs = positiveSafeInteger(input.statusTimestampMs);
99939
+ if (statusMs == null) return false;
99940
+ const sign = input.isLong ? 1 : -1;
99941
+ const chained = marketFillChain(input.fills, input.symbol);
99798
99942
  if (chained == null) return false;
99799
99943
  const before = chained.filter((row) => row.time <= statusMs);
99800
99944
  const after = chained.filter((row) => row.time > statusMs);
@@ -99947,7 +100091,7 @@ var init_protective_entry_cover = __esm({
99947
100091
  });
99948
100092
 
99949
100093
  // lib/runtime/native-position-protection.ts
99950
- var nativeProtectionSettings, memberSetting, KINDS, formatTriggerOrNull, nativePositionTriggerPrice, nativeEntryRequest, HALF_UP_DIGIT, roundDecimalHalfUp, nativeTrailingRetracement, nativeAfterFillActions, classifyNativeOrderEnd, isOpenInDirection, nativePlacementGate, nativeStrayOrderDecision, FIRED_TRIGGER_CONDITION, TRAILING_ORDER_TYPE, closingSide, DECIMAL_PATTERN, decimalUnits2, fractionDigits, nativePlaceCover, positiveOrderId, nativeRearmDecision, nativeLostStopCrossed, readListedProtectiveRow, explainAbsentProtectiveOrder, readServerNativeProtectionState;
100094
+ var nativeProtectionSettings, memberSetting, KINDS, formatTriggerOrNull, nativePositionTriggerPrice, nativeEntryRequest, HALF_UP_DIGIT, roundDecimalHalfUp, nativeTrailingRetracement, nativeAfterFillActions, classifyNativeOrderEnd, isOpenInDirection, nativePlacementGate, nativeStrayOrderDecision, FIRED_TRIGGER_CONDITION, TRAILING_ORDER_TYPE, closingSide, DECIMAL_PATTERN, decimalUnits2, fractionDigits, nativePlaceCover, positiveOrderId, nativeRearmDecision, nativeLostStopCrossed, readListedProtectiveRow, explainAbsentProtectiveOrder, readServerNativeProtectionState, nativeFillOpenedPosition, nativePositionEndedSince, flatReadEndsPosition;
99951
100095
  var init_native_position_protection = __esm({
99952
100096
  "lib/runtime/native-position-protection.ts"() {
99953
100097
  "use strict";
@@ -100167,11 +100311,60 @@ var init_native_position_protection = __esm({
100167
100311
  if (typeof record5.enabled !== "boolean" || legacy == null || native == null) return null;
100168
100312
  return { enabled: record5.enabled, legacySymbols: new Set(legacy), nativeSymbols: new Set(native) };
100169
100313
  };
100314
+ nativeFillOpenedPosition = (input) => {
100315
+ if (!input.complete || !Array.isArray(input.fills)) return "unknown";
100316
+ const market = normalizeHyperliquidMarketSymbol(input.symbol);
100317
+ const moves = [];
100318
+ const decimal = (value) => {
100319
+ const text = typeof value === "number" && Number.isFinite(value) ? String(value) : typeof value === "string" ? value.trim() : "";
100320
+ return DECIMAL_PATTERN.test(text) ? Number(text) : null;
100321
+ };
100322
+ for (const fill of input.fills) {
100323
+ if (fill == null || typeof fill !== "object" || Array.isArray(fill)) continue;
100324
+ const record5 = fill;
100325
+ if (String(record5.oid ?? "").trim() !== input.orderId.trim()) continue;
100326
+ if (normalizeHyperliquidMarketSymbol(String(record5.coin ?? "")) !== market) continue;
100327
+ const start = decimal(record5.startPosition);
100328
+ const size = decimal(record5.sz);
100329
+ if (start == null || size == null || size <= 0 || record5.side !== "B" && record5.side !== "A") return "unknown";
100330
+ moves.push({ start, end: start + (record5.side === "B" ? size : -size) });
100331
+ }
100332
+ if (moves.length === 0) return "unknown";
100333
+ if (moves.some(({ start, end }) => noExposureOnSide(start, input.isLong) && !noExposureOnSide(end, input.isLong))) {
100334
+ return "opened";
100335
+ }
100336
+ if (moves.every(({ start }) => !noExposureOnSide(start, input.isLong))) return "joined";
100337
+ if (moves.every(({ end }) => noExposureOnSide(end, input.isLong))) return "other_side";
100338
+ return "unknown";
100339
+ };
100340
+ nativePositionEndedSince = (input) => {
100341
+ let answer = "unknown";
100342
+ const chain = input.complete ? marketFillChain(input.fills, input.symbol) : null;
100343
+ if (chain != null) {
100344
+ let last = -1;
100345
+ chain.forEach((row, index) => {
100346
+ if (row.orderId === input.orderId.trim()) last = index;
100347
+ });
100348
+ if (last >= 0) {
100349
+ answer = chain.slice(last).some((row) => noExposureOnSide(row.end, input.isLong)) ? "ended" : "open";
100350
+ }
100351
+ }
100352
+ if (answer === "unknown" && input.flatRead != null && flatReadEndsPosition(input.flatRead, input.isLong)) return "ended";
100353
+ return answer;
100354
+ };
100355
+ flatReadEndsPosition = (read, isLong) => {
100356
+ if (read.pageComplete !== true || read.newestFillMs === void 0) return false;
100357
+ const text = String(read.position ?? "").trim();
100358
+ if (!DECIMAL_PATTERN.test(text) || !Number.isSafeInteger(read.stateMs)) return false;
100359
+ if (!noExposureOnSide(Number(text), isLong)) return false;
100360
+ if (read.newestFillMs == null) return true;
100361
+ return Number.isSafeInteger(read.newestFillMs) && read.newestFillMs < read.stateMs;
100362
+ };
100170
100363
  }
100171
100364
  });
100172
100365
 
100173
100366
  // lib/runtime/native-protection-device.ts
100174
- var NATIVE_PROTECTION_RECORD_VERSION, nativeProtectionStorage, resolveStorage, setNativeProtectionStorage, recordKey, isMember, isRetracement, isLot, readNativeProtectionRecord, versioned, writeNativeProtectionRecord, NativeOrderNotSentError, withDispatchBoundary, attempt, notSentRestores, errorText, actionOf, isOpenInDirection2, coverRows, restingOrderIdAt, definitivelyRefused, TRAILING_LOT_FIRED, ownLotOrderIds, lotRetracement, lotReport, sendTrailingLot, planNativeFillLot, dropNativePendingLot, planNativePendingLot, planNativeOpen, recordEntryChildren, observeMembers, UNKNOWN_ORDER_RESPONSE, resolveUnknownOrderIds, settleNativeProtectionAfterFill, reconcileNativeProtection;
100367
+ var NATIVE_PROTECTION_RECORD_VERSION, nativeProtectionStorage, resolveStorage, setNativeProtectionStorage, recordKey, isMember, isRetracement, isLot, isStandbyAdd, readNativeProtectionRecord, versioned, writeNativeProtectionRecord, NO_FILLS, nativeFillsPageFromUserFills, fillsReader, flatReadOf, orderFillTimes, namedOrderId, NativeOrderNotSentError, withDispatchBoundary, attempt, notSentRestores, errorText, actionOf, isOpenInDirection2, coverRows, restingOrderIdAt, definitivelyRefused, TRAILING_LOT_FIRED, TRAILING_LOT_POSITION_ENDED, TRAILING_LOT_OTHER_SIDE, lotFillLeftPosition, lotOfAdd, ORDER_ID_PATTERN, lotFillOrderId, lotPositionSince, ownLotOrderIds, lotRetracement, lotReport, sendTrailingLot, planNativeFillLot, planNativeStandbyAdd, nameNativeStandbyAdd, dropNativeStandbyAdd, dropNativePendingLot, planNativePendingLot, planNativeOpen, recordEntryChildren, observeMembers, UNKNOWN_ORDER_RESPONSE, resolveUnknownOrderIds, plannedPair, resolveStandbyAdds, settleNativeProtectionAfterFill, reconcileNativeProtection;
100175
100368
  var init_native_protection_device = __esm({
100176
100369
  "lib/runtime/native-protection-device.ts"() {
100177
100370
  "use strict";
@@ -100179,6 +100372,8 @@ var init_native_protection_device = __esm({
100179
100372
  init_define_VTX_GROK_POLICY();
100180
100373
  init_define_VTX_PI_MODEL_POLICY();
100181
100374
  init_constants();
100375
+ init_hyperliquid_market_symbol();
100376
+ init_hyperliquid_order_status();
100182
100377
  init_order_identity();
100183
100378
  init_native_position_protection();
100184
100379
  NATIVE_PROTECTION_RECORD_VERSION = 1;
@@ -100199,7 +100394,7 @@ var init_native_protection_device = __esm({
100199
100394
  isMember = (value) => {
100200
100395
  if (!value || typeof value !== "object") return false;
100201
100396
  const member = value;
100202
- return (member.kind === "sl" || member.kind === "tp") && typeof member.clientOrderId === "string" && (member.orderId === null || typeof member.orderId === "number" && Number.isSafeInteger(member.orderId)) && typeof member.trigger === "string" && (member.placedAtMs === null || typeof member.placedAtMs === "number") && typeof member.sentAtMs === "number" && typeof member.replacedOnce === "boolean" && (member.pendingModify === void 0 || typeof member.pendingModify === "object" && member.pendingModify !== null && typeof member.pendingModify.clientOrderId === "string" && typeof member.pendingModify.trigger === "string" && typeof member.pendingModify.sentAtMs === "number");
100397
+ return (member.kind === "sl" || member.kind === "tp") && typeof member.clientOrderId === "string" && (member.orderId === null || typeof member.orderId === "number" && Number.isSafeInteger(member.orderId)) && typeof member.trigger === "string" && (member.placedAtMs === null || typeof member.placedAtMs === "number") && typeof member.sentAtMs === "number" && typeof member.replacedOnce === "boolean" && (member.plannedAfterMs === void 0 || typeof member.plannedAfterMs === "number") && (member.pendingModify === void 0 || typeof member.pendingModify === "object" && member.pendingModify !== null && typeof member.pendingModify.clientOrderId === "string" && typeof member.pendingModify.trigger === "string" && typeof member.pendingModify.sentAtMs === "number");
100203
100398
  };
100204
100399
  isRetracement = (value) => {
100205
100400
  if (!value || typeof value !== "object") return false;
@@ -100210,7 +100405,12 @@ var init_native_protection_device = __esm({
100210
100405
  isLot = (value) => {
100211
100406
  if (!value || typeof value !== "object") return false;
100212
100407
  const lot = value;
100213
- return (lot.mutationId === null || typeof lot.mutationId === "string") && typeof lot.fillKey === "string" && typeof lot.fillEventMs === "number" && typeof lot.size === "string" && isRetracement(lot.retracement) && (lot.orderId === null || typeof lot.orderId === "number" && Number.isSafeInteger(lot.orderId)) && (lot.placedAtMs === null || typeof lot.placedAtMs === "number") && typeof lot.sentAtMs === "number" && typeof lot.replacedOnce === "boolean" && (lot.userCancelledOrderId === void 0 || typeof lot.userCancelledOrderId === "number") && (lot.fillEventFromDevice === void 0 || typeof lot.fillEventFromDevice === "boolean") && (lot.retiredReason === void 0 || typeof lot.retiredReason === "string");
100408
+ return (lot.mutationId === null || typeof lot.mutationId === "string") && typeof lot.fillKey === "string" && (lot.fillOrderId === void 0 || typeof lot.fillOrderId === "string") && typeof lot.fillEventMs === "number" && typeof lot.size === "string" && isRetracement(lot.retracement) && (lot.orderId === null || typeof lot.orderId === "number" && Number.isSafeInteger(lot.orderId)) && (lot.placedAtMs === null || typeof lot.placedAtMs === "number") && typeof lot.sentAtMs === "number" && typeof lot.replacedOnce === "boolean" && (lot.userCancelledOrderId === void 0 || typeof lot.userCancelledOrderId === "number") && (lot.fillEventFromDevice === void 0 || typeof lot.fillEventFromDevice === "boolean") && (lot.retiredReason === void 0 || typeof lot.retiredReason === "string");
100409
+ };
100410
+ isStandbyAdd = (value) => {
100411
+ if (!value || typeof value !== "object") return false;
100412
+ const add = value;
100413
+ return typeof add.clientOrderId === "string" && (add.orderId === null || typeof add.orderId === "string") && typeof add.sentAtMs === "number";
100214
100414
  };
100215
100415
  readNativeProtectionRecord = (profileId, symbol2) => {
100216
100416
  const storage3 = resolveStorage();
@@ -100218,7 +100418,7 @@ var init_native_protection_device = __esm({
100218
100418
  const raw = storage3.getItem(recordKey(profileId, symbol2));
100219
100419
  if (raw == null) return null;
100220
100420
  const parsed = JSON.parse(raw);
100221
- if (parsed?.version !== NATIVE_PROTECTION_RECORD_VERSION && parsed?.version !== NATIVE_PROTECTION_RECORD_WITH_LOTS_VERSION || parsed.profileId !== profileId || parsed.symbol !== symbol2 || typeof parsed.walletAddress !== "string" || typeof parsed.isLong !== "boolean" || parsed.phase !== "entry_pending" && parsed.phase !== "active" || typeof parsed.entryMutationId !== "string" || typeof parsed.entryClientOrderId !== "string" || typeof parsed.createdAtMs !== "number" || !Array.isArray(parsed.members) || !parsed.members.every(isMember) || parsed.lots !== void 0 && (parsed.version !== NATIVE_PROTECTION_RECORD_WITH_LOTS_VERSION || !Array.isArray(parsed.lots) || !parsed.lots.every(isLot))) {
100421
+ if (parsed?.version !== NATIVE_PROTECTION_RECORD_VERSION && parsed?.version !== NATIVE_PROTECTION_RECORD_WITH_LOTS_VERSION || parsed.profileId !== profileId || parsed.symbol !== symbol2 || typeof parsed.walletAddress !== "string" || typeof parsed.isLong !== "boolean" || parsed.phase !== "entry_pending" && parsed.phase !== "active" || typeof parsed.entryMutationId !== "string" || typeof parsed.entryClientOrderId !== "string" || typeof parsed.createdAtMs !== "number" || !Array.isArray(parsed.members) || !parsed.members.every(isMember) || parsed.lots !== void 0 && (parsed.version !== NATIVE_PROTECTION_RECORD_WITH_LOTS_VERSION || !Array.isArray(parsed.lots) || !parsed.lots.every(isLot)) || parsed.standby !== void 0 && (!Array.isArray(parsed.standby) || !parsed.standby.every(isStandbyAdd)) || parsed.positionOrderId !== void 0 && typeof parsed.positionOrderId !== "string") {
100222
100422
  throw new Error("Stored native protection record is invalid.");
100223
100423
  }
100224
100424
  return parsed;
@@ -100238,6 +100438,63 @@ var init_native_protection_device = __esm({
100238
100438
  return false;
100239
100439
  }
100240
100440
  };
100441
+ NO_FILLS = { fills: [], complete: false, coversFromMs: null };
100442
+ nativeFillsPageFromUserFills = (rawFills, evidence) => {
100443
+ const live = evidence.source === "live";
100444
+ if (evidence.providerRowCount < evidence.providerPageCap) return { fills: [...rawFills], complete: live, coversFromMs: null };
100445
+ const oldest = evidence.oldestFillTimeMs;
100446
+ if (oldest == null) return NO_FILLS;
100447
+ return {
100448
+ fills: rawFills.filter((fill) => Number(fill?.time) > oldest),
100449
+ complete: live,
100450
+ coversFromMs: oldest + 1
100451
+ };
100452
+ };
100453
+ fillsReader = (io) => {
100454
+ let read = null;
100455
+ return () => {
100456
+ read ??= io.readFills().catch((error48) => {
100457
+ if (io.endsPass?.(error48)) throw error48;
100458
+ return NO_FILLS;
100459
+ });
100460
+ return read;
100461
+ };
100462
+ };
100463
+ flatReadOf = (position, page, symbol2) => {
100464
+ const stateMs = position.stateTimeMs;
100465
+ if (!page.complete || stateMs == null || !Number.isSafeInteger(stateMs)) return null;
100466
+ const market = normalizeHyperliquidMarketSymbol(symbol2);
100467
+ let newest = null;
100468
+ for (const fill of page.fills) {
100469
+ if (fill == null || typeof fill !== "object" || Array.isArray(fill)) continue;
100470
+ const row = fill;
100471
+ if (normalizeHyperliquidMarketSymbol(String(row.coin ?? "")) !== market) continue;
100472
+ const time3 = Number(row.time);
100473
+ if (!Number.isSafeInteger(time3)) return null;
100474
+ newest = newest == null ? time3 : Math.max(newest, time3);
100475
+ }
100476
+ return {
100477
+ position: String(position.size),
100478
+ stateMs,
100479
+ newestFillMs: newest,
100480
+ pageComplete: page.coversFromMs == null || page.coversFromMs < stateMs
100481
+ };
100482
+ };
100483
+ orderFillTimes = (page, orderId, symbol2) => {
100484
+ const market = normalizeHyperliquidMarketSymbol(symbol2);
100485
+ return page.fills.flatMap((fill) => {
100486
+ if (fill == null || typeof fill !== "object" || Array.isArray(fill)) return [];
100487
+ const row = fill;
100488
+ if (String(row.oid ?? "").trim() !== orderId.trim()) return [];
100489
+ if (normalizeHyperliquidMarketSymbol(String(row.coin ?? "")) !== market) return [];
100490
+ const time3 = Number(row.time);
100491
+ return [Number.isSafeInteger(time3) && time3 > 0 ? time3 : Number.NaN];
100492
+ });
100493
+ };
100494
+ namedOrderId = (evidence) => {
100495
+ const orderId = Number(evidence.orderId);
100496
+ return evidence.responseValid && evidence.orderMatches && Number.isSafeInteger(orderId) && orderId > 0 ? String(orderId) : null;
100497
+ };
100241
100498
  NativeOrderNotSentError = class extends Error {
100242
100499
  constructor(cause) {
100243
100500
  super(cause instanceof Error ? cause.message : "The exchange call failed before dispatch.");
@@ -100303,6 +100560,24 @@ var init_native_protection_device = __esm({
100303
100560
  return Array.isArray(statuses) && statuses.length > 0 && statuses.every((status) => Boolean(status && typeof status === "object" && "error" in status));
100304
100561
  };
100305
100562
  TRAILING_LOT_FIRED = "protective_trailing_lot_fired";
100563
+ TRAILING_LOT_POSITION_ENDED = "protective_trailing_lot_position_ended";
100564
+ TRAILING_LOT_OTHER_SIDE = "protective_trailing_lot_other_side";
100565
+ lotFillLeftPosition = (lot) => lot.retiredReason === TRAILING_LOT_FIRED || lot.retiredReason === TRAILING_LOT_POSITION_ENDED || lot.retiredReason === TRAILING_LOT_OTHER_SIDE;
100566
+ lotOfAdd = (lot, add) => lot.fillKey === add.clientOrderId || add.orderId != null && (lot.fillKey === add.orderId || lot.fillOrderId === add.orderId);
100567
+ ORDER_ID_PATTERN = /^\d+$/;
100568
+ lotFillOrderId = (lot) => lot.fillOrderId ?? (ORDER_ID_PATTERN.test(lot.fillKey) ? lot.fillKey : null);
100569
+ lotPositionSince = async (lot, record5, fills) => {
100570
+ const orderId = lotFillOrderId(lot);
100571
+ if (orderId == null) return "unknown";
100572
+ const page = await fills();
100573
+ return nativePositionEndedSince({
100574
+ fills: page.fills,
100575
+ complete: page.complete,
100576
+ orderId,
100577
+ isLong: record5.isLong,
100578
+ symbol: record5.symbol
100579
+ });
100580
+ };
100306
100581
  ownLotOrderIds = (record5) => (record5.lots ?? []).flatMap((lot) => lot.orderId == null ? [] : [lot.orderId]);
100307
100582
  lotRetracement = (settings, size, sizeDecimals) => {
100308
100583
  const stopLoss = settings.stopLoss;
@@ -100385,6 +100660,22 @@ var init_native_protection_device = __esm({
100385
100660
  else lots.push(planned);
100386
100661
  return { ...record5, lots };
100387
100662
  };
100663
+ planNativeStandbyAdd = (record5, input) => {
100664
+ if (!input.clientOrderId || (record5.standby ?? []).some((add) => add.clientOrderId === input.clientOrderId)) return record5;
100665
+ return {
100666
+ ...record5,
100667
+ standby: [...record5.standby ?? [], { clientOrderId: input.clientOrderId, orderId: null, sentAtMs: input.nowMs }]
100668
+ };
100669
+ };
100670
+ nameNativeStandbyAdd = (record5, clientOrderId, orderId) => (record5.standby ?? []).some((add) => add.clientOrderId === clientOrderId && add.orderId !== orderId) ? {
100671
+ ...record5,
100672
+ standby: (record5.standby ?? []).map((add) => add.clientOrderId === clientOrderId ? { ...add, orderId } : add)
100673
+ } : record5;
100674
+ dropNativeStandbyAdd = (record5, clientOrderId) => {
100675
+ const standby = (record5.standby ?? []).filter((add) => add.clientOrderId !== clientOrderId);
100676
+ const { standby: _dropped, ...rest } = record5;
100677
+ return standby.length > 0 ? { ...rest, standby } : rest;
100678
+ };
100388
100679
  dropNativePendingLot = (record5, key) => versioned({
100389
100680
  ...record5,
100390
100681
  lots: (record5.lots ?? []).filter((lot) => !(lot.fillKey === key && lot.mutationId == null && lot.size === ""))
@@ -100495,7 +100786,7 @@ var init_native_protection_device = __esm({
100495
100786
  }
100496
100787
  continue;
100497
100788
  }
100498
- if (member.orderId != null || member.retiredReason) {
100789
+ if (member.orderId != null || member.retiredReason || member.plannedAfterMs != null) {
100499
100790
  members.push(member);
100500
100791
  continue;
100501
100792
  }
@@ -100508,6 +100799,109 @@ var init_native_protection_device = __esm({
100508
100799
  }
100509
100800
  return { ...record5, members };
100510
100801
  };
100802
+ plannedPair = (settings, afterMs, io) => ["sl", "tp"].filter((kind) => (kind === "sl" ? settings.stopLoss : settings.takeProfit) != null).map((kind) => ({
100803
+ kind,
100804
+ clientOrderId: clientOrderIdForMutation(io.newMutationId()),
100805
+ orderId: null,
100806
+ trigger: "",
100807
+ placedAtMs: null,
100808
+ sentAtMs: io.nowMs(),
100809
+ replacedOnce: false,
100810
+ plannedAfterMs: afterMs
100811
+ }));
100812
+ resolveStandbyAdds = async (args) => {
100813
+ const { io } = args;
100814
+ let record5 = args.record;
100815
+ const standby = record5.standby ?? [];
100816
+ if (standby.length === 0) return { record: record5, addFillMs: null, undecided: false };
100817
+ const left = [];
100818
+ let addFillMs = null;
100819
+ for (const add of standby) {
100820
+ if (left.length > 0) {
100821
+ left.push(add);
100822
+ continue;
100823
+ }
100824
+ let orderId = add.orderId;
100825
+ let endedUnfilledAtMs = null;
100826
+ if (orderId == null) {
100827
+ const evidence = await io.readOrderStatus(add.clientOrderId);
100828
+ orderId = namedOrderId(evidence);
100829
+ if (orderId == null) {
100830
+ if (!(evidence.responseStatus === UNKNOWN_ORDER_RESPONSE && io.nowMs() > io.neverLandsAfterMs(add.sentAtMs))) {
100831
+ left.push(add);
100832
+ }
100833
+ continue;
100834
+ }
100835
+ if (classifyHyperliquidOrderStatus(evidence.orderStatus) === "terminal_unfilled") {
100836
+ endedUnfilledAtMs = evidence.orderTimestampMs ?? null;
100837
+ }
100838
+ }
100839
+ const page = await args.fills();
100840
+ const times = orderFillTimes(page, orderId, record5.symbol);
100841
+ const verdict = nativeFillOpenedPosition({
100842
+ fills: page.fills,
100843
+ complete: page.complete,
100844
+ orderId,
100845
+ isLong: record5.isLong,
100846
+ symbol: record5.symbol
100847
+ });
100848
+ const fillMs = times.length > 0 && times.every(Number.isFinite) ? Math.max(...times) : null;
100849
+ if (verdict === "other_side") {
100850
+ const lots = record5.lots ?? [];
100851
+ if (lots.some((lot) => lotOfAdd(lot, { clientOrderId: add.clientOrderId, orderId }))) {
100852
+ record5 = {
100853
+ ...record5,
100854
+ lots: lots.map((lot) => lotOfAdd(lot, { clientOrderId: add.clientOrderId, orderId }) && !lot.retiredReason ? { ...lot, retiredReason: TRAILING_LOT_OTHER_SIDE } : lot)
100855
+ };
100856
+ }
100857
+ continue;
100858
+ }
100859
+ if (verdict === "unknown" || fillMs == null) {
100860
+ const neverFilled = endedUnfilledAtMs != null && page.complete && times.length === 0 && (page.coversFromMs == null || page.coversFromMs <= endedUnfilledAtMs);
100861
+ if (neverFilled) continue;
100862
+ let pageAccountsForAdd = times.length > 0;
100863
+ if (!pageAccountsForAdd && page.coversFromMs != null) {
100864
+ const evidence = await io.readOrderStatus(orderId);
100865
+ const endedMs = evidence.statusTimestampMs;
100866
+ pageAccountsForAdd = evidence.responseValid && evidence.terminal && endedMs != null && endedMs < page.coversFromMs;
100867
+ }
100868
+ const positionEnded = nativePositionEndedSince({
100869
+ fills: page.fills,
100870
+ complete: page.complete,
100871
+ orderId,
100872
+ isLong: record5.isLong,
100873
+ symbol: record5.symbol,
100874
+ flatRead: pageAccountsForAdd ? flatReadOf(args.position, page, record5.symbol) : null
100875
+ }) === "ended";
100876
+ if (!positionEnded) left.push(add);
100877
+ continue;
100878
+ }
100879
+ const stateMs = args.position.stateTimeMs;
100880
+ if (stateMs == null || !(stateMs > fillMs)) {
100881
+ left.push(add);
100882
+ continue;
100883
+ }
100884
+ record5 = { ...record5, positionOrderId: orderId };
100885
+ addFillMs = fillMs;
100886
+ if (verdict === "opened") {
100887
+ const resting = record5.members.filter((member) => member.orderId != null && !member.retiredReason && args.page.some((order) => order.oid === member.orderId));
100888
+ const planned = plannedPair(args.settings, fillMs, io);
100889
+ record5 = {
100890
+ ...record5,
100891
+ members: [
100892
+ ...planned.map((member) => {
100893
+ const kept = resting.find((entry) => entry.kind === member.kind);
100894
+ return kept ? { ...kept, replacedOnce: false } : member;
100895
+ }),
100896
+ // A kind the settings no longer enable stays tracked while it rests.
100897
+ ...resting.filter((entry) => !planned.some((member) => member.kind === entry.kind))
100898
+ ]
100899
+ };
100900
+ }
100901
+ }
100902
+ const { standby: _decided, ...rest } = record5;
100903
+ return { record: left.length > 0 ? { ...rest, standby: left } : rest, addFillMs, undecided: left.length > 0 };
100904
+ };
100511
100905
  settleNativeProtectionAfterFill = async (input) => {
100512
100906
  const { io } = input;
100513
100907
  const reports = [];
@@ -100516,6 +100910,17 @@ var init_native_protection_device = __esm({
100516
100910
  const page = await io.readOpenOrders();
100517
100911
  const position = await io.readPosition();
100518
100912
  const symbol2 = record5.symbol;
100913
+ const fills = fillsReader(io);
100914
+ const settlingAdds = (record5.standby ?? []).length > 0;
100915
+ const boundary = await resolveStandbyAdds({ record: record5, settings: input.settings, io, fills, position, page });
100916
+ record5 = boundary.record;
100917
+ if (boundary.undecided) {
100918
+ return { record: record5, reports };
100919
+ }
100920
+ const entryOrderId = String(input.entryOrderId ?? "").trim();
100921
+ if (record5.positionOrderId == null && boundary.addFillMs == null && !settlingAdds && ORDER_ID_PATTERN.test(entryOrderId)) {
100922
+ record5 = { ...record5, positionOrderId: entryOrderId };
100923
+ }
100519
100924
  if (!isOpenInDirection2(position.size, record5.isLong)) {
100520
100925
  reports.push({
100521
100926
  order_id: input.entryOrderId,
@@ -100554,7 +100959,10 @@ var init_native_protection_device = __esm({
100554
100959
  });
100555
100960
  let eventMs = Math.max(
100556
100961
  0,
100557
- ...observations.map((entry) => entry.row?.timestamp ?? entry.member.placedAtMs ?? 0)
100962
+ ...observations.map((entry) => entry.row?.timestamp ?? entry.member.placedAtMs ?? 0),
100963
+ // An add's own fill, and the fill a planned pair answers: Hyperliquid's times.
100964
+ boundary.addFillMs ?? 0,
100965
+ ...record5.members.map((member) => member.plannedAfterMs ?? 0)
100558
100966
  );
100559
100967
  if (eventMs <= 0 && input.entryOrderId) {
100560
100968
  const entryStatus = await io.readOrderStatus(input.entryOrderId);
@@ -100634,7 +101042,7 @@ var init_native_protection_device = __esm({
100634
101042
  });
100635
101043
  continue;
100636
101044
  }
100637
- if (existing != null && existing.orderId == null && !unknownClientOrderIds.has(existing.clientOrderId)) {
101045
+ if (existing != null && existing.orderId == null && existing.plannedAfterMs == null && !unknownClientOrderIds.has(existing.clientOrderId)) {
100638
101046
  continue;
100639
101047
  }
100640
101048
  if (gate !== "place") {
@@ -100753,8 +101161,15 @@ var init_native_protection_device = __esm({
100753
101161
  const retracement = lotRetracement(input.settings, size, input.sizeDecimals);
100754
101162
  if (retracement) {
100755
101163
  const { fillEventFromDevice: _deviceTime, ...withoutDeviceTime } = journaledLot;
100756
- const planned = eventMs > 0 ? { ...withoutDeviceTime, size, retracement, fillEventMs: eventMs } : { ...journaledLot, size, retracement };
100757
- if (gate === "place") {
101164
+ let planned = eventMs > 0 ? { ...withoutDeviceTime, size, retracement, fillEventMs: eventMs } : { ...journaledLot, size, retracement };
101165
+ if (gate === "place" && lotFillOrderId(planned) == null) {
101166
+ const named = namedOrderId(await io.readOrderStatus(planned.fillKey));
101167
+ if (named != null) planned = { ...planned, fillOrderId: named };
101168
+ }
101169
+ const since = gate === "place" ? await lotPositionSince(planned, record5, fills) : "unknown";
101170
+ if (since === "ended") {
101171
+ lots[lotIndex] = { ...planned, retiredReason: TRAILING_LOT_POSITION_ENDED };
101172
+ } else if (since === "open") {
100758
101173
  const index = lotIndex;
100759
101174
  const sent = await sendTrailingLot({
100760
101175
  io,
@@ -100800,6 +101215,28 @@ var init_native_protection_device = __esm({
100800
101215
  const position = await io.readPosition();
100801
101216
  const symbol2 = record5.symbol;
100802
101217
  const stateMs = position.stateTimeMs ?? Number.NEGATIVE_INFINITY;
101218
+ const fills = fillsReader(io);
101219
+ const undecidedAdds = (record5.standby ?? []).length > 0;
101220
+ let membersPositionEnded = null;
101221
+ const membersEnded = () => {
101222
+ membersPositionEnded ??= (async () => {
101223
+ let anchor = record5.positionOrderId ?? null;
101224
+ if (anchor == null) {
101225
+ anchor = namedOrderId(await io.readOrderStatus(record5.entryClientOrderId));
101226
+ if (anchor != null) record5 = { ...record5, positionOrderId: anchor };
101227
+ }
101228
+ const fillsPage = await fills();
101229
+ return nativePositionEndedSince({
101230
+ fills: fillsPage.fills,
101231
+ complete: fillsPage.complete,
101232
+ orderId: anchor ?? "",
101233
+ isLong: record5.isLong,
101234
+ symbol: symbol2,
101235
+ flatRead: flatReadOf(position, fillsPage, symbol2)
101236
+ });
101237
+ })();
101238
+ return membersPositionEnded;
101239
+ };
100803
101240
  const observations = observeMembers(record5, page).map((entry) => ({
100804
101241
  ...entry,
100805
101242
  member: entry.row ? { ...entry.member, placedAtMs: entry.row.timestamp || entry.member.placedAtMs } : entry.member
@@ -100971,6 +101408,33 @@ var init_native_protection_device = __esm({
100971
101408
  members.push(member);
100972
101409
  continue;
100973
101410
  }
101411
+ if (member.plannedAfterMs != null) {
101412
+ if (!kindEnabled(member)) continue;
101413
+ const plannedGate = nativePlacementGate({
101414
+ eventMs: member.plannedAfterMs,
101415
+ position: position.size,
101416
+ positionStateMs: stateMs,
101417
+ isLong: record5.isLong
101418
+ });
101419
+ if (plannedGate === "not_required") continue;
101420
+ const plannedTrigger = currentTrigger(member);
101421
+ if (plannedGate === "need_reads" || plannedTrigger == null) {
101422
+ anyResting = true;
101423
+ members.push(member);
101424
+ continue;
101425
+ }
101426
+ const placed = await placeMember({
101427
+ member,
101428
+ trigger: plannedTrigger,
101429
+ replacedOnce: false,
101430
+ eventMs: member.plannedAfterMs,
101431
+ reasonCode: "protective_native_position_opened_by_add",
101432
+ observationIndex
101433
+ });
101434
+ members.push(placed);
101435
+ if (!placed.retiredReason) anyResting = true;
101436
+ continue;
101437
+ }
100974
101438
  if (member.orderId == null) {
100975
101439
  if (io.nowMs() <= io.neverLandsAfterMs(member.sentAtMs) || !unknownClientOrderIds.has(member.clientOrderId)) {
100976
101440
  anyResting = true;
@@ -101014,10 +101478,9 @@ var init_native_protection_device = __esm({
101014
101478
  });
101015
101479
  explained = end2 === "resting" || end2 === "pending" || end2 === "unknown" ? "status_read" : "ended_with_position";
101016
101480
  }
101017
- if (explained !== "ended_with_position") {
101018
- anyResting = true;
101019
- members.push(member);
101020
- }
101481
+ if (explained === "ended_with_position" && await membersEnded() === "ended") continue;
101482
+ anyResting = true;
101483
+ members.push(member);
101021
101484
  continue;
101022
101485
  }
101023
101486
  const evidence = await io.readOrderStatus(member.orderId);
@@ -101039,7 +101502,7 @@ var init_native_protection_device = __esm({
101039
101502
  });
101040
101503
  if (rearm === "retire" || !kindEnabled(member)) continue;
101041
101504
  const rearmTrigger = currentTrigger(member);
101042
- if (rearm === "need_reads" || rearmTrigger == null) {
101505
+ if (rearm === "need_reads" || rearmTrigger == null || undecidedAdds) {
101043
101506
  members.push(member);
101044
101507
  continue;
101045
101508
  }
@@ -101124,7 +101587,8 @@ var init_native_protection_device = __esm({
101124
101587
  for (const [index, prior] of priorLots.entries()) {
101125
101588
  let lot = prior;
101126
101589
  const restingRow = lot.orderId == null ? null : page.find((order) => order.oid === lot.orderId) ?? null;
101127
- if ((lot.retiredReason || lot.userCancelledOrderId != null) && !(restingRow && readListedProtectiveRow({ triggerCondition: restingRow.trigger_condition }) === "resting")) {
101590
+ const otherSideUnnamed = lot.retiredReason === TRAILING_LOT_OTHER_SIDE && lot.mutationId != null && lot.orderId == null;
101591
+ if ((lot.retiredReason || lot.userCancelledOrderId != null) && !otherSideUnnamed && !(restingRow && readListedProtectiveRow({ triggerCondition: restingRow.trigger_condition }) === "resting")) {
101128
101592
  lots.push(lot);
101129
101593
  continue;
101130
101594
  }
@@ -101133,7 +101597,8 @@ var init_native_protection_device = __esm({
101133
101597
  const entryStatus = await io.readOrderStatus(lot.fillKey);
101134
101598
  if (entryStatus.responseValid && entryStatus.orderMatches && entryStatus.statusTimestampMs != null) {
101135
101599
  const { fillEventFromDevice: _deviceTime, ...exchangeTimed } = lot;
101136
- lot = { ...exchangeTimed, fillEventMs: entryStatus.statusTimestampMs };
101600
+ const named = lotFillOrderId(lot) == null ? namedOrderId(entryStatus) : null;
101601
+ lot = { ...exchangeTimed, fillEventMs: entryStatus.statusTimestampMs, ...named != null ? { fillOrderId: named } : {} };
101137
101602
  } else if (entryStatus.responseStatus === UNKNOWN_ORDER_RESPONSE && io.nowMs() > io.neverLandsAfterMs(lot.sentAtMs)) {
101138
101603
  continue;
101139
101604
  } else {
@@ -101154,9 +101619,28 @@ var init_native_protection_device = __esm({
101154
101619
  lots.push(lot);
101155
101620
  continue;
101156
101621
  }
101622
+ if (lotFillOrderId(lot) == null) {
101623
+ const named = namedOrderId(await io.readOrderStatus(lot.fillKey));
101624
+ if (named != null) lot = { ...lot, fillOrderId: named };
101625
+ }
101626
+ if ((record5.standby ?? []).some((add) => lotOfAdd(lot, add))) {
101627
+ anyResting = true;
101628
+ lots.push(lot);
101629
+ continue;
101630
+ }
101631
+ const since = await lotPositionSince(lot, record5, fills);
101632
+ if (since === "ended") {
101633
+ lots.push({ ...lot, retiredReason: TRAILING_LOT_POSITION_ENDED });
101634
+ continue;
101635
+ }
101636
+ if (since !== "open") {
101637
+ anyResting = true;
101638
+ lots.push(lot);
101639
+ continue;
101640
+ }
101157
101641
  if (!lot.size) {
101158
101642
  const others = [...lots, ...priorLots.slice(index + 1)];
101159
- const covered = others.reduce((total, other) => other.size && other.retiredReason !== TRAILING_LOT_FIRED ? total + Number(other.size) : total, 0);
101643
+ const covered = others.reduce((total, other) => other.size && !lotFillLeftPosition(other) ? total + Number(other.size) : total, 0);
101160
101644
  const uncovered = Number((Math.abs(position.size) - covered).toFixed(input.sizeDecimals));
101161
101645
  if (!(uncovered > 0)) continue;
101162
101646
  lot = { ...lot, size: String(uncovered) };
@@ -101183,11 +101667,24 @@ var init_native_protection_device = __esm({
101183
101667
  const named = answer != null && (answer.status === "settled" && answer.outcome_code === "success" || answer.status === "reconciled" && answer.outcome_code === "exchange_effect_observed") && Number.isSafeInteger(orderId) && orderId > 0;
101184
101668
  if (named) {
101185
101669
  lot = { ...lot, orderId };
101670
+ } else if (lot.retiredReason && (answer?.status === "settled" && answer.outcome_code === "rejected" || answer?.status === "reconciled" && answer.outcome_code === "exchange_expired_unconfirmed" || answer?.status === "absent" && io.nowMs() > io.neverLandsAfterMs(lot.sentAtMs))) {
101671
+ lots.push({ ...lot, mutationId: null });
101672
+ continue;
101186
101673
  } else if (answer?.status === "settled" && answer.outcome_code === "rejected") {
101187
101674
  lots.push({ ...lot, retiredReason: "protective_place_rejected" });
101188
101675
  continue;
101189
101676
  } else if (answer?.status === "reconciled" && answer.outcome_code === "exchange_expired_unconfirmed" || answer?.status === "absent" && io.nowMs() > io.neverLandsAfterMs(lot.sentAtMs)) {
101190
101677
  if (!positionOpen) continue;
101678
+ const since = await lotPositionSince(lot, record5, fills);
101679
+ if (since === "ended") {
101680
+ lots.push({ ...lot, retiredReason: TRAILING_LOT_POSITION_ENDED });
101681
+ continue;
101682
+ }
101683
+ if (since !== "open") {
101684
+ anyResting = true;
101685
+ lots.push(lot);
101686
+ continue;
101687
+ }
101191
101688
  const sent2 = await sendTrailingLot({ io, symbol: symbol2, lot: { ...lot, mutationId: null }, journal: (next) => journalLot(index, next) });
101192
101689
  lots.push(sent2.lot);
101193
101690
  if (sent2.report) reports.push(sent2.report);
@@ -101203,7 +101700,7 @@ var init_native_protection_device = __esm({
101203
101700
  const row = lot === prior ? restingRow : page.find((order) => order.oid === lotOrderId) ?? null;
101204
101701
  if (row && readListedProtectiveRow({ triggerCondition: row.trigger_condition }) === "resting") {
101205
101702
  lot = { ...lot, placedAtMs: row.timestamp || lot.placedAtMs };
101206
- const stray = nativeStrayOrderDecision({
101703
+ const stray = lot.retiredReason === TRAILING_LOT_OTHER_SIDE ? "cancel" : nativeStrayOrderDecision({
101207
101704
  placedMs: lot.placedAtMs ?? Number.POSITIVE_INFINITY,
101208
101705
  position: position.size,
101209
101706
  positionStateMs: stateMs,
@@ -101282,6 +101779,15 @@ var init_native_protection_device = __esm({
101282
101779
  lots.push(lot);
101283
101780
  continue;
101284
101781
  }
101782
+ const lostSince = await lotPositionSince(lot, record5, fills);
101783
+ if (lostSince === "ended") {
101784
+ lots.push({ ...lot, retiredReason: TRAILING_LOT_POSITION_ENDED });
101785
+ continue;
101786
+ }
101787
+ if (lostSince !== "open") {
101788
+ lots.push(lot);
101789
+ continue;
101790
+ }
101285
101791
  const sent = await sendTrailingLot({
101286
101792
  io,
101287
101793
  symbol: symbol2,
@@ -101293,7 +101799,7 @@ var init_native_protection_device = __esm({
101293
101799
  if (sent.report) reports.push(sent.report);
101294
101800
  if (!sent.lot.retiredReason) anyResting = true;
101295
101801
  }
101296
- if (!positionOpen && !anyResting) {
101802
+ if (!positionOpen && !anyResting && !undecidedAdds) {
101297
101803
  return { record: null, reports };
101298
101804
  }
101299
101805
  const { lots: _priorLots, ...withoutLots } = record5;
@@ -105020,6 +105526,19 @@ var init_runtime_execution = __esm({
105020
105526
  if (mutation.operation_kind !== "trailing_stop") throw new Error("The ledger names another action for this trailing lot.");
105021
105527
  return { status: mutation.status, outcome_code: mutation.outcome_code, exchange_order_id: mutation.exchange_order_id };
105022
105528
  },
105529
+ // The device's own fills read (Client Mode: every Hyperliquid read comes
105530
+ // from the device), fresh, as the per-entry lane's episode rule reads it.
105531
+ readFills: async () => {
105532
+ const { rawFills, evidence } = await fetchBrowserUserFills({
105533
+ publicRequestPriority: "trading_reduce",
105534
+ config: request.config ?? {},
105535
+ walletAddress,
105536
+ symbols: [symbol2],
105537
+ forceRefresh: true,
105538
+ signal: request.signal
105539
+ });
105540
+ return nativeFillsPageFromUserFills(rawFills, evidence);
105541
+ },
105023
105542
  isDefinitiveRefusal: (error48) => error48 instanceof HyperliquidExchangeRejectionError || error48 instanceof NativeOrderNotSentError,
105024
105543
  neverLandsAfterMs: (sentAtMs) => clientOrderNeverLandsAfterMs(request.config, { kind: "absent", ageStartMs: sentAtMs }),
105025
105544
  newMutationId: () => createRuntimeId().toLowerCase(),
@@ -105053,17 +105572,29 @@ var init_runtime_execution = __esm({
105053
105572
  if (read.record.walletAddress !== wallet) return [nativeStorageReport(symbol2, "protective_wallet_mismatch")];
105054
105573
  try {
105055
105574
  const io = nativeProtectionIo(request, read.record.isLong);
105056
- if (read.record.phase === "entry_pending") {
105057
- const settled = await settleNativeProtectionAfterFill({
105575
+ const standby = read.record.standby ?? [];
105576
+ if (read.record.phase === "entry_pending" || standby.length > 0) {
105577
+ const settled2 = await settleNativeProtectionAfterFill({
105058
105578
  record: read.record,
105059
105579
  settings: nativeSettingsOf(request.executionContext),
105060
105580
  sizeDecimals: request.executionContext.sizeDecimals,
105061
105581
  fillSize: "0",
105062
- entryOrderId: read.record.entryClientOrderId,
105582
+ entryOrderId: read.record.phase === "entry_pending" ? read.record.entryClientOrderId : standby[0].orderId ?? standby[0].clientOrderId,
105063
105583
  io
105064
105584
  });
105065
- const reports2 = [...settled.reports];
105066
- if (!writeNativeProtectionRecord(profileId, symbol2, settled.record)) {
105585
+ const reports2 = [...settled2.reports];
105586
+ let record5 = settled2.record;
105587
+ if (record5 != null && record5.phase !== "entry_pending" && (record5.standby ?? []).length > 0) {
105588
+ const kept = await reconcileNativeProtection({
105589
+ record: record5,
105590
+ settings: nativeSettingsOf(request.executionContext),
105591
+ sizeDecimals: request.executionContext.sizeDecimals,
105592
+ io
105593
+ });
105594
+ reports2.push(...kept.reports);
105595
+ record5 = kept.record;
105596
+ }
105597
+ if (!writeNativeProtectionRecord(profileId, symbol2, record5)) {
105067
105598
  reports2.push(nativeStorageReport(symbol2, "protective_lifecycle_persistence_failed"));
105068
105599
  }
105069
105600
  return reports2;
@@ -108314,6 +108845,7 @@ var init_runtime_execution = __esm({
108314
108845
  price: executionPrice,
108315
108846
  // A flip's close has filled by now: its new position starts from flat.
108316
108847
  currentPositionSize: targetResolution.closeOpposingPosition ? 0 : currentPositionSize,
108848
+ reduceOnly: classified.reduceOnly === true,
108317
108849
  maxOrderNotional: runtime_policy_generated_default2.trading.risk.max_order_notional,
108318
108850
  maxPositionNotional: runtime_policy_generated_default2.trading.risk.max_position_notional
108319
108851
  });
@@ -108439,13 +108971,14 @@ var init_runtime_execution = __esm({
108439
108971
  entryMutationId ??= createRuntimeId().toLowerCase();
108440
108972
  entryClientOrderId = clientOrderIdForMutation(entryMutationId);
108441
108973
  nativePendingLotKey = entryClientOrderId;
108442
- nativeAddRecord = planNativePendingLot(existingNative.record, {
108974
+ const journaledAt = Date.now();
108975
+ nativeAddRecord = planNativeStandbyAdd(planNativePendingLot(existingNative.record, {
108443
108976
  settings: nativeSettingsOf(input.executionContext),
108444
108977
  sizeDecimals: input.executionContext.sizeDecimals,
108445
108978
  key: entryClientOrderId,
108446
108979
  sizeHint: sizeAsset,
108447
- nowMs: Date.now()
108448
- });
108980
+ nowMs: journaledAt
108981
+ }), { clientOrderId: entryClientOrderId, nowMs: journaledAt });
108449
108982
  if (nativeAddRecord !== existingNative.record && !writeNativeProtectionRecord(nativeProfileId, input.executionContext.symbol, nativeAddRecord)) {
108450
108983
  return nativeBlocked(
108451
108984
  "protective_lifecycle_persistence_failed",
@@ -108632,7 +109165,7 @@ var init_runtime_execution = __esm({
108632
109165
  writeNativeProtectionRecord(
108633
109166
  nativeProfileId,
108634
109167
  input.executionContext.symbol,
108635
- dropNativePendingLot(stored.record, nativePendingLotKey)
109168
+ dropNativeStandbyAdd(dropNativePendingLot(stored.record, nativePendingLotKey), nativePendingLotKey)
108636
109169
  );
108637
109170
  }
108638
109171
  }
@@ -108759,6 +109292,9 @@ var init_runtime_execution = __esm({
108759
109292
  let record5 = nativeOpen != null ? recordEntryChildren(nativeOpen.record, marketOrderResponse) : nativeAddRecord;
108760
109293
  let keepNativeJournal = false;
108761
109294
  if (confirmedMarketFill?.orderId) {
109295
+ if (nativeOpen == null && nativePendingLotKey != null) {
109296
+ record5 = nameNativeStandbyAdd(record5, nativePendingLotKey, String(confirmedMarketFill.orderId));
109297
+ }
108762
109298
  record5 = planNativeFillLot(record5, {
108763
109299
  settings: nativeSettingsOf(input.executionContext),
108764
109300
  sizeDecimals: input.executionContext.sizeDecimals,
@@ -108781,7 +109317,7 @@ var init_runtime_execution = __esm({
108781
109317
  });
108782
109318
  } else {
108783
109319
  try {
108784
- const settled = await settleNativeProtectionAfterFill({
109320
+ const settled2 = await settleNativeProtectionAfterFill({
108785
109321
  record: record5,
108786
109322
  settings: nativeSettingsOf(input.executionContext),
108787
109323
  sizeDecimals: input.executionContext.sizeDecimals,
@@ -108789,8 +109325,8 @@ var init_runtime_execution = __esm({
108789
109325
  entryOrderId: confirmedMarketFill.orderId,
108790
109326
  io: nativeProtectionIo(input, record5.isLong)
108791
109327
  });
108792
- executionReports.push(...settled.reports);
108793
- if (settled.record != null) record5 = settled.record;
109328
+ executionReports.push(...settled2.reports);
109329
+ if (settled2.record != null) record5 = settled2.record;
108794
109330
  } catch (postEntryProtectionError) {
108795
109331
  if (isClientRuntimeLeaseOwnershipError(postEntryProtectionError)) throw postEntryProtectionError;
108796
109332
  if (nativePassEnded(input, postEntryProtectionError)) {
@@ -109288,7 +109824,7 @@ var init_runtime_execution = __esm({
109288
109824
  let actualPosition = null;
109289
109825
  let desiredPosition = null;
109290
109826
  let exactFullCloseBeforeQuantization = false;
109291
- let maxOrderNotional = 0;
109827
+ let followerOrderNotionalCap = 0;
109292
109828
  let minOrderNotional = 0;
109293
109829
  let executionReferencePrice = Number(intent.source_price);
109294
109830
  let dispatchedOrder = null;
@@ -109299,13 +109835,21 @@ var init_runtime_execution = __esm({
109299
109835
  desiredPosition = Number(
109300
109836
  record5.target_space === "copied" ? copiedNowServed ? record5.copied_target_after : Number.NaN : record5.desired_destination_position_after
109301
109837
  );
109302
- maxOrderNotional = Number(
109303
- reconciliation.max_order_notional_usdc
109304
- );
109838
+ followerOrderNotionalCap = reconciliation.max_order_notional_usdc;
109305
109839
  minOrderNotional = Number(
109306
109840
  reconciliation.min_notional_usdc
109307
109841
  );
109308
109842
  }
109843
+ const platformOrderNotionalCap = input.config?.copy_trading?.execution?.max_per_intent_order_notional_usdc;
109844
+ let maxOrderNotional = 0;
109845
+ let orderNotionalCapResolved = false;
109846
+ if (copyOrderNotionalCap(followerOrderNotionalCap, platformOrderNotionalCap, 0) === null) {
109847
+ return {
109848
+ status: "failed",
109849
+ orderId: null,
109850
+ message: "Copy Trading platform order notional cap is unavailable."
109851
+ };
109852
+ }
109309
109853
  if (!destinationSide || !Number.isFinite(destinationSize) || destinationSize <= 0) {
109310
109854
  return {
109311
109855
  status: "skipped",
@@ -109381,6 +109925,17 @@ var init_runtime_execution = __esm({
109381
109925
  destinationSize = Math.abs(liveDelta);
109382
109926
  exactFullCloseBeforeQuantization = Math.abs(desiredPosition) <= tolerance && Math.abs(actualPosition) > tolerance;
109383
109927
  reduceOnly = Math.abs(desiredPosition) <= tolerance || (actualPosition > 0 && liveDelta < 0 && desiredPosition >= 0 || actualPosition < 0 && liveDelta > 0 && desiredPosition <= 0);
109928
+ maxOrderNotional = copyOrderNotionalCap(
109929
+ followerOrderNotionalCap,
109930
+ platformOrderNotionalCap,
109931
+ copyOrderClosingSize({
109932
+ side: destinationSide,
109933
+ size: destinationSize,
109934
+ reduceOnly,
109935
+ actualPosition
109936
+ }) * executionReferencePrice
109937
+ ) ?? 0;
109938
+ orderNotionalCapResolved = true;
109384
109939
  if (Number.isFinite(maxOrderNotional) && maxOrderNotional > 0) {
109385
109940
  destinationSize = Math.min(
109386
109941
  destinationSize,
@@ -109400,6 +109955,18 @@ var init_runtime_execution = __esm({
109400
109955
  };
109401
109956
  }
109402
109957
  const referencePrice = executionReferencePrice;
109958
+ if (!orderNotionalCapResolved) {
109959
+ maxOrderNotional = copyOrderNotionalCap(
109960
+ followerOrderNotionalCap,
109961
+ platformOrderNotionalCap,
109962
+ copyOrderClosingSize({
109963
+ side: destinationSide,
109964
+ size: destinationSize,
109965
+ reduceOnly,
109966
+ actualPosition: null
109967
+ }) * referencePrice
109968
+ ) ?? 0;
109969
+ }
109403
109970
  if (Number.isFinite(maxOrderNotional) && maxOrderNotional > 0 && Number.isFinite(referencePrice) && referencePrice > 0 && sizePrecision.quantizedSize * referencePrice > maxOrderNotional + COPY_TRADING_NOTIONAL_CAP_TOLERANCE_USD) {
109404
109971
  const cappedSize = Math.min(destinationSize, maxOrderNotional / referencePrice);
109405
109972
  sizePrecision = {
@@ -110026,7 +110593,7 @@ var init_periodic_schedule = __esm({
110026
110593
  });
110027
110594
 
110028
110595
  // lib/runtime/provider-observability.ts
110029
- var MAX_DIAGNOSTIC_LIST_ITEMS, record4, ERROR_TOKEN, ERROR_DOMAIN, ERROR_INPUT, ERROR_REDACTIONS, normalizeProviderError, identifier, count3, normalizeProviderDiagnostics, providerRequestId, hash4, googleCredentialDiagnostics, extractProviderDiagnostics, estimateRequestInputTokens;
110596
+ var MAX_DIAGNOSTIC_LIST_ITEMS, record4, ERROR_TOKEN, ERROR_DOMAIN, ERROR_INPUT, ERROR_ECHO_REDACTIONS, ERROR_PROSE_REDACTIONS, CONTROL_CHARACTER_RUN, WHITESPACE_RUN, collapseProse, settled, REDACTED_MARKER_START, boundedMessage, normalizeProviderError, identifier, count3, normalizeProviderDiagnostics, providerRequestId, hash4, googleCredentialDiagnostics, extractProviderDiagnostics, estimateRequestInputTokens;
110030
110597
  var init_provider_observability = __esm({
110031
110598
  "lib/runtime/provider-observability.ts"() {
110032
110599
  "use strict";
@@ -110034,34 +110601,68 @@ var init_provider_observability = __esm({
110034
110601
  init_define_VTX_GROK_POLICY();
110035
110602
  init_define_VTX_PI_MODEL_POLICY();
110036
110603
  init_constants();
110604
+ init_runtime_redaction();
110037
110605
  MAX_DIAGNOSTIC_LIST_ITEMS = PROVIDER_DIAGNOSTIC_LIMITS.MAX_LIST_ITEMS;
110038
110606
  record4 = (v) => v !== null && typeof v === "object" && !Array.isArray(v) ? v : {};
110039
110607
  ERROR_TOKEN = /^[A-Z][A-Z0-9_]{0,63}$/;
110040
110608
  ERROR_DOMAIN = /^[a-z0-9][a-z0-9.-]{0,127}$/;
110041
- ERROR_INPUT = /\b(?:prompt|contents|messages|system[_ ]?instruction|tools|request\s+body|input(?:\s+text)?)\s*[:=]|[{}]|```/i;
110042
- ERROR_REDACTIONS = [
110043
- [/https?:\/\/[^\s<>"']+/gi, "[REDACTED_URL]"],
110609
+ ERROR_INPUT = new RegExp(
110610
+ String.raw`\b(?:prompt|contents|messages|system[_ ]?instruction|tools|request${WHITESPACE_CLASS}+body|input(?:${WHITESPACE_CLASS}+text)?)${WHITESPACE_CLASS}*[:=]|[{}]|` + "```",
110611
+ "i"
110612
+ );
110613
+ ERROR_ECHO_REDACTIONS = [
110614
+ [/https?:\/\/[^<>"'\t\n\v\f\r \x1c-\x1f\x85\xa0\u1680\u2000-\u200a\u2028\u2029\u202f\u205f\u3000]+/gi, "[REDACTED_URL]"],
110044
110615
  [/\b[A-Za-z0-9.!#$%&'*+/=?^_`{|}~-]+@[A-Za-z0-9.-]+\.[A-Za-z]{2,}\b/g, "[REDACTED_EMAIL]"],
110045
- [/\bBearer\s+[^\s,;]+/gi, "Bearer [REDACTED]"],
110046
- [/\b(?:api[_ -]?key|x-goog-api-key|authorization|access[_ -]?token|token|secret|password|private[_ -]?key|key)\s*[:=]\s*(?:"[^"]*"|'[^']*'|[^\s,;]+)/gi, "[REDACTED]"],
110047
- [/\b(?:AIza[A-Za-z0-9_-]+|sk-[A-Za-z0-9_-]+|AQ\.[A-Za-z0-9._-]+|0x[a-fA-F0-9]{64})\b/g, "[REDACTED]"],
110616
+ // A URL whose scheme a key form already took ("AIzahttps://..." is read as
110617
+ // a key first): the rest is still an echoed URL.
110618
+ [/\[REDACTED\]:\/\/[^<>"'\t\n\v\f\r \x1c-\x1f\x85\xa0\u1680\u2000-\u200a\u2028\u2029\u202f\u205f\u3000]+/g, "[REDACTED_URL]"]
110619
+ ];
110620
+ ERROR_PROSE_REDACTIONS = [
110621
+ ...ERROR_ECHO_REDACTIONS,
110048
110622
  [/"[^"]*"|'[^'\r\n]*'/g, "[REDACTED]"]
110049
110623
  ];
110624
+ CONTROL_CHARACTER_RUN = /[\x00-\x1f\x7f]+/g;
110625
+ WHITESPACE_RUN = new RegExp(`${WHITESPACE_CLASS}+`, "g");
110626
+ collapseProse = (value) => value.replace(CONTROL_CHARACTER_RUN, " ").replace(WHITESPACE_RUN, " ").trim();
110627
+ settled = (value) => {
110628
+ let current = value;
110629
+ let previous = null;
110630
+ while (current !== previous) {
110631
+ previous = current;
110632
+ for (const [pattern, replacement] of ERROR_PROSE_REDACTIONS) current = current.replace(pattern, replacement);
110633
+ current = sanitizeRuntimeDiagnosticValue(collapseProse(current));
110634
+ }
110635
+ return current;
110636
+ };
110637
+ REDACTED_MARKER_START = "[REDACTED";
110638
+ boundedMessage = (value) => {
110639
+ const characters = Array.from(value);
110640
+ if (characters.length <= PROVIDER_DIAGNOSTIC_LIMITS.MAX_ERROR_MESSAGE_CHARS) return value;
110641
+ let cut = characters.slice(0, PROVIDER_DIAGNOSTIC_LIMITS.MAX_ERROR_MESSAGE_CHARS).join("");
110642
+ const marker = cut.lastIndexOf(REDACTED_MARKER_START);
110643
+ if (marker !== -1 && value.indexOf("]", marker) >= cut.length) cut = cut.slice(0, marker);
110644
+ return cut.replace(/ +$/, "");
110645
+ };
110050
110646
  normalizeProviderError = (value) => {
110051
110647
  const raw = record4(value);
110052
110648
  const result = {};
110053
110649
  if (typeof raw.code === "number" && Number.isInteger(raw.code) && raw.code >= HTTP_STATUS_MIN && raw.code <= HTTP_STATUS_MAX) result.code = raw.code;
110054
110650
  if (typeof raw.status === "string" && ERROR_TOKEN.test(raw.status)) result.status = raw.status;
110055
- if (typeof raw.message === "string" && raw.message.trim()) {
110651
+ if (typeof raw.message === "string" && collapseProse(raw.message)) {
110056
110652
  let message = raw.message;
110057
- if (Array.from(message).length > PROVIDER_DIAGNOSTIC_LIMITS.MAX_ERROR_INPUT_CHARS || ERROR_INPUT.test(message)) message = "[REDACTED_INPUT]";
110653
+ if (Array.from(message).length > PROVIDER_DIAGNOSTIC_LIMITS.MAX_ERROR_INPUT_CHARS || ERROR_INPUT.test(message) || ERROR_INPUT.test(collapseProse(message))) message = "[REDACTED_INPUT]";
110058
110654
  else {
110059
- for (const [pattern, replacement] of ERROR_REDACTIONS) message = message.replace(pattern, replacement);
110060
- message = message.replace(/[\x00-\x1f\x7f]+/g, " ").replace(/\s+/g, " ").trim();
110061
- }
110062
- const characters = Array.from(message);
110063
- result.message = characters.slice(0, PROVIDER_DIAGNOSTIC_LIMITS.MAX_ERROR_MESSAGE_CHARS).join("");
110064
- if (characters.length > PROVIDER_DIAGNOSTIC_LIMITS.MAX_ERROR_MESSAGE_CHARS || raw.message_truncated === true) result.message_truncated = true;
110655
+ message = sanitizeRuntimeDiagnosticValue(message);
110656
+ for (const [pattern, replacement] of ERROR_ECHO_REDACTIONS) message = message.replace(pattern, replacement);
110657
+ message = sanitizeRuntimeDiagnosticValue(message);
110658
+ for (const [pattern, replacement] of ERROR_PROSE_REDACTIONS) message = message.replace(pattern, replacement);
110659
+ message = settled(sanitizeRuntimeDiagnosticValue(collapseProse(sanitizeRuntimeDiagnosticValue(message))));
110660
+ }
110661
+ const fullLength = Array.from(message).length;
110662
+ let bounded = boundedMessage(message);
110663
+ while (settled(bounded) !== bounded) bounded = Array.from(bounded).slice(0, -1).join("").replace(/ +$/, "");
110664
+ result.message = bounded;
110665
+ if (fullLength > PROVIDER_DIAGNOSTIC_LIMITS.MAX_ERROR_MESSAGE_CHARS || raw.message_truncated === true) result.message_truncated = true;
110065
110666
  }
110066
110667
  if (Array.isArray(raw.details)) {
110067
110668
  const details = raw.details.slice(0, PROVIDER_DIAGNOSTIC_LIMITS.MAX_ERROR_DETAILS).map((value2) => {
@@ -113599,7 +114200,7 @@ var init_profile_model_cascade = __esm({
113599
114200
  });
113600
114201
 
113601
114202
  // lib/runtime/prompt-variable-validation-contract.ts
113602
- var ESCAPED_OPEN_BRACE, ESCAPED_CLOSE_BRACE, PROMPT_PLACEHOLDER_PATTERN, ESCAPED_BRACE_PAIR_PATTERN, readPromptTemplate, restoreEscapedBraces, countAtMost, countBelow, locatePlaceholders, isPromptVariableName, renderPromptTemplate, promptTemplatePlaceholderSpans, promptTemplatePlaceholders, promptTemplateVariables, NEWS_PROMPT_VARIABLES, REFERENCE_CANDLES_PROMPT_VARIABLE, ALLOWED_PROMPT_VARIABLES, OPTIONAL_BLANK_PROMPT_VARIABLES, coercePromptVariableValue, isMissingPromptVariableValue, validatePromptVariables;
114203
+ var ESCAPED_OPEN_BRACE, ESCAPED_CLOSE_BRACE, PROMPT_PLACEHOLDER_PATTERN, ESCAPED_BRACE_PAIR_PATTERN, readPromptTemplate, restoreEscapedBraces, countAtMost, countBelow, locatePlaceholders, isPromptVariableName, renderPromptTemplate, formatInstructionTemplate, promptTemplatePlaceholderSpans, promptTemplatePlaceholders, promptTemplateVariables, NEWS_PROMPT_VARIABLES, REFERENCE_CANDLES_PROMPT_VARIABLE, ALLOWED_PROMPT_VARIABLES, OPTIONAL_BLANK_PROMPT_VARIABLES, coercePromptVariableValue, isMissingPromptVariableValue, validatePromptVariables;
113603
114204
  var init_prompt_variable_validation_contract = __esm({
113604
114205
  "lib/runtime/prompt-variable-validation-contract.ts"() {
113605
114206
  "use strict";
@@ -113685,6 +114286,40 @@ var init_prompt_variable_validation_contract = __esm({
113685
114286
  rendered.push(prepared.slice(cursor));
113686
114287
  return restoreEscapedBraces(rendered.join(""));
113687
114288
  };
114289
+ formatInstructionTemplate = (template, values, label2 = "instruction template") => {
114290
+ const text = String(template || "");
114291
+ const rendered = [];
114292
+ let index = 0;
114293
+ while (index < text.length) {
114294
+ const char = text[index];
114295
+ const escapedPair = `${char}${char}`;
114296
+ if ((char === "{" || char === "}") && text.startsWith(escapedPair, index)) {
114297
+ rendered.push(char);
114298
+ index += escapedPair.length;
114299
+ continue;
114300
+ }
114301
+ if (char === "}") {
114302
+ throw new Error(`Invalid ${label2}: ${template}`);
114303
+ }
114304
+ if (char !== "{") {
114305
+ rendered.push(char);
114306
+ index += 1;
114307
+ continue;
114308
+ }
114309
+ const end = text.indexOf("}", index + 1);
114310
+ const field = end < 0 ? "" : text.slice(index + 1, end);
114311
+ const name = field.endsWith(":") ? field.slice(0, -1) : field;
114312
+ if (!/^[a-zA-Z_][a-zA-Z0-9_]*$/.test(name)) {
114313
+ throw new Error(`Invalid ${label2}: ${template}`);
114314
+ }
114315
+ if (!Object.prototype.hasOwnProperty.call(values, name)) {
114316
+ throw new Error(`Unexpected ${label2} placeholder: ${name}`);
114317
+ }
114318
+ rendered.push(String(values[name]));
114319
+ index = end + 1;
114320
+ }
114321
+ return rendered.join("");
114322
+ };
113688
114323
  promptTemplatePlaceholderSpans = (template) => {
113689
114324
  if (typeof template !== "string" || !template) {
113690
114325
  return [];
@@ -116242,7 +116877,7 @@ var init_provider_client = __esm({
116242
116877
  return payload.message.trim();
116243
116878
  }
116244
116879
  if (rawText) {
116245
- return rawText.replace(/\s+/g, " ").slice(0, PROVIDER_ERROR_RAW_TEXT_MAX_CHARS);
116880
+ return sanitizeRuntimeDiagnosticValue(rawText).replace(/\s+/g, " ").slice(0, PROVIDER_ERROR_RAW_TEXT_MAX_CHARS);
116246
116881
  }
116247
116882
  return "";
116248
116883
  };
@@ -118420,7 +119055,7 @@ var init_provider_client = __esm({
118420
119055
  });
118421
119056
 
118422
119057
  // lib/runtime/prompt-contract.ts
118423
- var PROMPT_PLACEHOLDER_MAP, DATA_FORMAT_TAG_ALIASES, buildDecisionInstructionVariables, renderCandleIndicatorDefinitions, NEWS_COLUMN_DESCRIPTIONS, isNewsPromptTag, newsTagBlock, newsRowColumns, renderNewsLegendLine, behaviorStateHasObjectField, candleBlockPayload, candlesHaveLiveField, templateReferencesTag, templateTagOrder, renderDataFormatLegend, replaceEmbeddedDataFormatLegend, SIZE_AMOUNT_USDC_LABEL_PATTERN, labelSizeAmountInUsd, canonicalizePromptPlaceholders, normalizePromptWhitespace, formatInstructionTemplate, constructPromptSystemTemplate;
119058
+ var PROMPT_PLACEHOLDER_MAP, DATA_FORMAT_TAG_ALIASES, buildDecisionInstructionVariables, renderCandleIndicatorDefinitions, NEWS_COLUMN_DESCRIPTIONS, isNewsPromptTag, newsTagBlock, newsRowColumns, renderNewsLegendLine, behaviorStateHasObjectField, candleBlockPayload, candlesHaveLiveField, templateReferencesTag, templateTagOrder, renderDataFormatLegend, replaceEmbeddedDataFormatLegend, SIZE_AMOUNT_USDC_LABEL_PATTERN, labelSizeAmountInUsd, canonicalizePromptPlaceholders, normalizePromptWhitespace, constructPromptSystemTemplate;
118424
119059
  var init_prompt_contract = __esm({
118425
119060
  "lib/runtime/prompt-contract.ts"() {
118426
119061
  "use strict";
@@ -118837,28 +119472,6 @@ var init_prompt_contract = __esm({
118837
119472
  }
118838
119473
  return text.replace(/\r\n/g, "\n").replace(/[\t ]{2,}\n/g, "\n").replace(/\n{3,}/g, "\n\n").trim();
118839
119474
  };
118840
- formatInstructionTemplate = (template, vars) => {
118841
- const escapedOpen = "__VTX_INSTR_OPEN_BRACE__";
118842
- const escapedClose = "__VTX_INSTR_CLOSE_BRACE__";
118843
- const prepared = String(template ?? "").replaceAll("{{", escapedOpen).replaceAll("}}", escapedClose);
118844
- const replacements = [];
118845
- const formatted = prepared.replace(/\{([a-zA-Z0-9_]+)\}/g, (_match, key) => {
118846
- if (!Object.prototype.hasOwnProperty.call(vars, key)) {
118847
- throw new Error(`Unexpected instruction template placeholder: ${key}`);
118848
- }
118849
- const marker = `__VTX_INSTR_VALUE_${replacements.length}__`;
118850
- replacements.push(String(vars[key]));
118851
- return marker;
118852
- });
118853
- if (/[{}]/.test(formatted)) {
118854
- throw new Error(`Invalid instruction template: ${template}`);
118855
- }
118856
- let rendered = formatted.replaceAll(escapedOpen, "{").replaceAll(escapedClose, "}");
118857
- replacements.forEach((value, index) => {
118858
- rendered = rendered.replaceAll(`__VTX_INSTR_VALUE_${index}__`, value);
118859
- });
118860
- return rendered;
118861
- };
118862
119475
  constructPromptSystemTemplate = (systemTemplate, options) => {
118863
119476
  const instructions = options.instructions ?? {};
118864
119477
  const symbols = (options.symbols ?? []).map((symbol2) => String(symbol2).trim()).filter(Boolean);
@@ -119730,7 +120343,7 @@ __export(local_analysis_exports, {
119730
120343
  runLocalRuntimeCycle: () => runLocalRuntimeCycle,
119731
120344
  summarizeReviewFailureExplanation: () => summarizeReviewFailureExplanation
119732
120345
  });
119733
- var CYCLE_TIMEOUT_FLOOR_MS, DECISION_SETTLEMENT_RESERVE_MAX_BUDGET_DIVISOR, MIN_AGENT_INSTRUCTION_RETRY_AFTER_MS, PROMPT_PARITY_ERROR_DETAIL_MAX_CHARS, EXTERNAL_INFERENCE_RUNTIME_POLL_INTERVAL_MS, REVIEW_PROVIDER_SERVER_ERROR_STATUSES, TRUNCATION_ELLIPSIS2, normalizeNativeValues, assertPromptModelController, resolveRuntimeReasoningControlsForModel, modelScopedKey, resolveNativeValuesForModel, observeRuntimeCycle, observeAccountState, aiOrderSlippageFraction, serverBehaviorStateArtifacts, ClientRuntimeAgentInstructionEmpty, isClientRuntimeAgentInstructionEmpty, ClientRuntimeAiSchedulePaused, ClientRuntimeAiScheduleStillActive, isClientRuntimeAiScheduleStillActive, ServerDispatchAccountStateStale, isServerDispatchAccountStateStale, isClientRuntimeAiSchedulePaused, acceptancePositionCaps, accountSnapshotCapturedAt, buildClaimedAgentRuntimeCycleResult, resolveRuntimeMarginModePreference, resolveRuntimeLeveragePreference, resolveBooleanSetting2, CLIENT_RUNTIME_LIVE_CONTEXT_UNAVAILABLE_ERRORS, BEHAVIOR_STATE_UNAVAILABLE_ERROR, CriticalBehaviorStateError, BEHAVIOR_MEMORY_UNAVAILABLE_ERROR, BehaviorMemoryUnavailableError, clampNumber, resolveExternalInferenceRuntimeTimeoutSeconds, toPositiveFinite3, compactSnippet, hashRuntimeDebugText, EFFECTIVE_INPUT_MANIFEST_SCHEMA_VERSION, PROMPT_ASSEMBLY_DEFINITION_VERSION, RUNTIME_SOURCE_DEFINITION_VERSION, DECISION_INPUT_DEFINITION_VERSION, CONTEXT_ENVELOPE_DEFINITION_VERSION, CLIENT_RUNTIME_SOURCE_VERSION, CLIENT_MAIN_PROMPT_RENDERER, SERVER_MAIN_PROMPT_RENDERER, CLIENT_REVIEW_PROMPT_RENDERER, SERVER_REVIEW_PROMPT_RENDERER, resolveEffectivePromptRuntimeProvenance, canonicalManifestValue, canonicalManifestJson, sha256ManifestHex, effectiveInputComponent, buildEffectiveInputManifest, MANIFEST_COMPONENT_NAME, derivePromptVisibleSections, decodeDecisionTracePayload, extractDecisionSymbolTrace, formatDecisionSymbolTrace, formatActionableDecisionSymbols, decisionRecordsBySymbol, normalizePromptSymbols, JSON_MODEL_OUTPUT_FENCE_PATTERN, STRICT_MODEL_OUTPUT_KEYS, currentModelOutputValidationErrors, currentModelOutputMatchesContract, projectCurrentModelDecisionContent, modelOutputValidationError, SERVER_UNREADABLE_REPLY_HOLD_REASONING, buildMissingDecisionHold, buildDecisionPlansFromResponse, buildReviewCandidatePlansFromResponse, forceUnavailableSymbolsToHold, extractTemplatePlaceholders, requireReviewPrimaryUserPromptTemplate, containsCompetingBehaviorStateMarkup, containsCompetingMainBehaviorStateMarkup, requireStrategyReviewTemplates, preflightStrategyReviewPromptContract, extractRuntimeReasoningSelection, isAbortError, isRuntimeTimeoutAbortReason, REVIEW_FAILURE_SENSITIVE_DB_TOKENS, REVIEW_FAILURE_SCHEMA_DISCLOSURE_TOKENS, REVIEW_FAILURE_SQL_STATEMENT_PATTERN, REVIEW_FAILURE_TRACEBACK_PATTERN, isSensitiveReviewFailureDetail, summarizeReviewFailureExplanation, buildReviewFailureHoldReason, createAbortError2, settleRuntimeCyclePromise, unwrapRuntimeCycleSettledResult, normalizeDecisionLabel, normalizeRuntimeSymbol, PromptContractFetchError, isLivePromptContextUnavailableError, buildFailClosedHoldResult, buildPromptConstructionFailureResult, buildLivePromptContextUnavailableFailureResult, pickFirstString, normalizeRuntimeStringList, requirePositiveRuntimeLimit, resolveRuntimeTradingScope, normalizeRuntimeProviderAlias, resolveCatalogModelEntry, createClientRuntimeProviderSetupError, createProviderSetupRejectionError, evaluateModelEligibility, extractReviewRuntimeReasoningSelection, isUsableRuntimeSettingsFallback, resolveRuntimeSettings, formatRuntimeDurationMs, normalizeRuntimeTimingNote, appendRuntimeTimingEvent, reportPromptParityTelemetry, resolveLocalRuntimeSecretRequirements, resolveLocalRuntimeSecretProvider, toEpochSeconds, AI_INDICATOR_KEYS_NEWER_THAN_SOME_SERVERS, sortTradingTimeframes, normalizePromptIdentityTimestamp, resolveCompletedCandleBoundary, normalizeAiIndicatorFlags, getPromptLookback, computeSma, computeEma, computeRsi, computeAtr, computeMacd, computeBollingerBands, getIndicatorValue, buildPromptCandlesComponent, buildPromptCandleTimeframeComponent, resolvePromptRelativeVolumeContext, promptRelativeVolumeBaseline, CANDLE_CLOSE_TICKER_TIMEFRAME, candleCloseTicker, buildPromptCandlesPayload, formatUtcTimestampWithWeekday, formatUtcNowWithWeekday, formatPromptPrice, capacityUnitSize, computePromptUnitsUsedForPosition, buildPromptAccountStatusValue, buildPromptPositionsValue, sanitizePromptSymbol, fillTimeMs, fillSize, normalizeFillSide, normalizeFillOrderId, normalizeFillRiskOrderIdentity, fillStartPosition, fillSortValue, sortFillsAscending, sortFillsDescending, inferEntryFromStartPositionChain, inferEntryFromCurrentPositionSize, calculateCurrentPositionState, calculatePositionEntryTimes, countPositionAdds, latestPositionRiskIncreaseTimeMs, latestPositionRiskIncreaseEvidence, compactPromptRiskIncrease, roundPositiveDecimalHalfUp, compactPromptLastTrade, ENTRY_TRADE_FIELDS, PREVIOUS_DECISION_FIELDS, PREVIOUS_CAMPAIGN_FIELDS, hasExactKeys2, isNonnegativeInteger, isFiniteNumber, isExactEnumString, isNonemptyPromptText, isCampaignReasoningText, projectBackendDecisionMemoryItem, requireRenderedStrategyBehaviorState, canonicalFillSideForRiskEvidence, isValidRiskEvidenceFill, isValidCampaignBoundaryFill, normalizeFillHistoryCoverage, resolveFillHistoryCoverageForSymbol, buildPromptBehaviorStateArtifacts, buildPromptBehaviorStateValue, shouldCompareServerPromptParity, buildLocalRuntimePromptArtifacts, createRuntimeId2, asRecord, buildRuntimeConstraintRejectionMessage, hasDeviceProviderSecret, requireNonEmptyStringField, requirePositiveIntegerField, compareContractVersion, parsePromptContractTimestamp, assertPromptContractCompatibility, assertPromptContractTemporalBounds, sleepWithAbort, requireAgentPollRetryAfterMs, materializeClaimedClientRuntimeAgentInstruction, attachClientRuntimeErrorProvenance, isExternalRuntimeProviderResult, invokeClientExternalInference, assertPromptContractBindingTupleEqual, assertPromptContractScopeMatch, fetchBoundPromptContracts, formatTemplateWithNamedVariables, carryReturnedModelCalls, runLocalRuntimeCycle;
120346
+ var CYCLE_TIMEOUT_FLOOR_MS, DECISION_SETTLEMENT_RESERVE_MAX_BUDGET_DIVISOR, MIN_AGENT_INSTRUCTION_RETRY_AFTER_MS, PROMPT_PARITY_ERROR_DETAIL_MAX_CHARS, EXTERNAL_INFERENCE_RUNTIME_POLL_INTERVAL_MS, REVIEW_PROVIDER_SERVER_ERROR_STATUSES, TRUNCATION_ELLIPSIS2, normalizeNativeValues, assertPromptModelController, resolveRuntimeReasoningControlsForModel, modelScopedKey, resolveNativeValuesForModel, observeRuntimeCycle, observeAccountState, aiOrderSlippageFraction, serverBehaviorStateArtifacts, ClientRuntimeAgentInstructionEmpty, isClientRuntimeAgentInstructionEmpty, ClientRuntimeAiSchedulePaused, ClientRuntimeAiScheduleStillActive, isClientRuntimeAiScheduleStillActive, ServerDispatchAccountStateStale, isServerDispatchAccountStateStale, isClientRuntimeAiSchedulePaused, acceptancePositionCaps, accountSnapshotCapturedAt, buildClaimedAgentRuntimeCycleResult, resolveRuntimeMarginModePreference, resolveRuntimeLeveragePreference, resolveBooleanSetting2, CLIENT_RUNTIME_LIVE_CONTEXT_UNAVAILABLE_ERRORS, BEHAVIOR_STATE_UNAVAILABLE_ERROR, CriticalBehaviorStateError, BEHAVIOR_MEMORY_UNAVAILABLE_ERROR, BehaviorMemoryUnavailableError, clampNumber, resolveExternalInferenceRuntimeTimeoutSeconds, toPositiveFinite3, compactSnippet, hashRuntimeDebugText, EFFECTIVE_INPUT_MANIFEST_SCHEMA_VERSION, PROMPT_ASSEMBLY_DEFINITION_VERSION, RUNTIME_SOURCE_DEFINITION_VERSION, DECISION_INPUT_DEFINITION_VERSION, CONTEXT_ENVELOPE_DEFINITION_VERSION, CLIENT_RUNTIME_SOURCE_VERSION, CLIENT_MAIN_PROMPT_RENDERER, SERVER_MAIN_PROMPT_RENDERER, CLIENT_REVIEW_PROMPT_RENDERER, SERVER_REVIEW_PROMPT_RENDERER, resolveEffectivePromptRuntimeProvenance, canonicalManifestValue, canonicalManifestJson, sha256ManifestHex, effectiveInputComponent, buildEffectiveInputManifest, MANIFEST_COMPONENT_NAME, derivePromptVisibleSections, decodeDecisionTracePayload, extractDecisionSymbolTrace, formatDecisionSymbolTrace, formatActionableDecisionSymbols, decisionRecordsBySymbol, normalizePromptSymbols, JSON_MODEL_OUTPUT_FENCE_PATTERN, STRICT_MODEL_OUTPUT_KEYS, currentModelOutputValidationErrors, currentModelOutputMatchesContract, projectCurrentModelDecisionContent, modelOutputValidationError, SERVER_UNREADABLE_REPLY_HOLD_REASONING, buildMissingDecisionHold, buildDecisionPlansFromResponse, buildReviewCandidatePlansFromResponse, forceUnavailableSymbolsToHold, extractTemplatePlaceholders, requireReviewPrimaryUserPromptTemplate, containsCompetingBehaviorStateMarkup, containsCompetingMainBehaviorStateMarkup, requireStrategyReviewTemplates, preflightStrategyReviewPromptContract, extractRuntimeReasoningSelection, isAbortError, isRuntimeTimeoutAbortReason, REVIEW_FAILURE_SENSITIVE_DB_TOKENS, REVIEW_FAILURE_SCHEMA_DISCLOSURE_TOKENS, REVIEW_FAILURE_SQL_STATEMENT_PATTERN, REVIEW_FAILURE_TRACEBACK_PATTERN, isSensitiveReviewFailureDetail, summarizeReviewFailureExplanation, buildReviewFailureHoldReason, createAbortError2, settleRuntimeCyclePromise, unwrapRuntimeCycleSettledResult, normalizeDecisionLabel, normalizeRuntimeSymbol, PromptContractFetchError, isLivePromptContextUnavailableError, buildFailClosedHoldResult, buildPromptConstructionFailureResult, buildLivePromptContextUnavailableFailureResult, pickFirstString, normalizeRuntimeStringList, requirePositiveRuntimeLimit, resolveRuntimeTradingScope, normalizeRuntimeProviderAlias, resolveCatalogModelEntry, createClientRuntimeProviderSetupError, createProviderSetupRejectionError, evaluateModelEligibility, extractReviewRuntimeReasoningSelection, isUsableRuntimeSettingsFallback, resolveRuntimeSettings, formatRuntimeDurationMs, normalizeRuntimeTimingNote, appendRuntimeTimingEvent, reportPromptParityTelemetry, resolveLocalRuntimeSecretRequirements, resolveLocalRuntimeSecretProvider, toEpochSeconds, AI_INDICATOR_KEYS_NEWER_THAN_SOME_SERVERS, sortTradingTimeframes, normalizePromptIdentityTimestamp, resolveCompletedCandleBoundary, normalizeAiIndicatorFlags, getPromptLookback, computeSma, computeEma, computeRsi, computeAtr, computeMacd, computeBollingerBands, getIndicatorValue, buildPromptCandlesComponent, buildPromptCandleTimeframeComponent, resolvePromptRelativeVolumeContext, promptRelativeVolumeBaseline, CANDLE_CLOSE_TICKER_TIMEFRAME, candleCloseTicker, buildPromptCandlesPayload, formatUtcTimestampWithWeekday, formatUtcNowWithWeekday, formatPromptPrice, capacityUnitSize, computePromptUnitsUsedForPosition, buildPromptAccountStatusValue, buildPromptPositionsValue, sanitizePromptSymbol, fillTimeMs, fillSize, normalizeFillSide, normalizeFillOrderId, normalizeFillRiskOrderIdentity, fillStartPosition, fillSortValue, sortFillsAscending, sortFillsDescending, inferEntryFromStartPositionChain, inferEntryFromCurrentPositionSize, calculateCurrentPositionState, calculatePositionEntryTimes, countPositionAdds, latestPositionRiskIncreaseTimeMs, latestPositionRiskIncreaseEvidence, compactPromptRiskIncrease, roundPositiveDecimalHalfUp, compactPromptLastTrade, ENTRY_TRADE_FIELDS, PREVIOUS_DECISION_FIELDS, PREVIOUS_CAMPAIGN_FIELDS, hasExactKeys2, isNonnegativeInteger, isFiniteNumber, isExactEnumString, isNonemptyPromptText, isCampaignReasoningText, projectBackendDecisionMemoryItem, requireRenderedStrategyBehaviorState, canonicalFillSideForRiskEvidence, isValidRiskEvidenceFill, isValidCampaignBoundaryFill, normalizeFillHistoryCoverage, resolveFillHistoryCoverageForSymbol, buildPromptBehaviorStateArtifacts, buildPromptBehaviorStateValue, shouldCompareServerPromptParity, buildLocalRuntimePromptArtifacts, createRuntimeId2, asRecord, buildRuntimeConstraintRejectionMessage, hasDeviceProviderSecret, requireNonEmptyStringField, requirePositiveIntegerField, compareContractVersion, parsePromptContractTimestamp, assertPromptContractCompatibility, assertPromptContractTemporalBounds, sleepWithAbort, requireAgentPollRetryAfterMs, materializeClaimedClientRuntimeAgentInstruction, attachClientRuntimeErrorProvenance, isExternalRuntimeProviderResult, invokeClientExternalInference, assertPromptContractBindingTupleEqual, assertPromptContractScopeMatch, fetchBoundPromptContracts, carryReturnedModelCalls, runLocalRuntimeCycle;
119734
120347
  var init_local_analysis = __esm({
119735
120348
  "lib/runtime/local-analysis.ts"() {
119736
120349
  "use strict";
@@ -120316,7 +120929,7 @@ var init_local_analysis = __esm({
120316
120929
  return numeric2;
120317
120930
  };
120318
120931
  compactSnippet = (value, max2 = RUNTIME_DEBUG_SNIPPET_CHARS) => {
120319
- const text = String(value ?? "").replace(/\s+/g, " ").trim();
120932
+ const text = sanitizeRuntimeDiagnosticValue(String(value ?? "").replace(/\s+/g, " ")).trim();
120320
120933
  if (!text) {
120321
120934
  return "";
120322
120935
  }
@@ -120910,29 +121523,27 @@ var init_local_analysis = __esm({
120910
121523
  return assembledUserTemplate;
120911
121524
  };
120912
121525
  preflightStrategyReviewPromptContract = (metadata, symbols, maxTrades) => {
121526
+ const reviewSystemTemplate = String(metadata.review_system_template ?? "");
121527
+ const reviewUserTemplate = String(metadata.review_user_template ?? "");
121528
+ if (!reviewSystemTemplate.trim() || !reviewUserTemplate.trim() || extractTemplatePlaceholders(reviewSystemTemplate).length > 0) {
121529
+ throw new CriticalBehaviorStateError();
121530
+ }
121531
+ requireStrategyReviewTemplates(reviewSystemTemplate, reviewUserTemplate);
120913
121532
  try {
120914
- requireStrategyReviewTemplates(
120915
- requireNonEmptyStringField(metadata.review_system_template, "review_system_template"),
120916
- requireNonEmptyStringField(metadata.review_user_template, "review_user_template")
120917
- );
120918
121533
  const reviewInstructions = asRecord(metadata.review_instructions);
120919
121534
  const reviewSecurity = requireNonEmptyStringField(
120920
121535
  reviewInstructions.review_security,
120921
121536
  "review_instructions.review_security"
120922
121537
  );
120923
- const reviewOutputContract = formatTemplateWithNamedVariables(
121538
+ const reviewOutputContract = formatInstructionTemplate(
120924
121539
  requireNonEmptyStringField(
120925
121540
  reviewInstructions.review_json_format,
120926
121541
  "review_instructions.review_json_format"
120927
121542
  ),
120928
121543
  buildDecisionInstructionVariables(symbols, maxTrades)
120929
121544
  );
120930
- const reviewSystemTemplate = requireNonEmptyStringField(
120931
- metadata.review_system_template,
120932
- "review_system_template"
120933
- );
120934
- if (extractTemplatePlaceholders(reviewSystemTemplate).length > 0 || extractTemplatePlaceholders(reviewSecurity).length > 0) {
120935
- throw new CriticalBehaviorStateError();
121545
+ if (extractTemplatePlaceholders(reviewSecurity).length > 0) {
121546
+ throw new BehaviorMemoryUnavailableError();
120936
121547
  }
120937
121548
  const securedReviewSystem = reviewSystemTemplate.includes(reviewSecurity) ? reviewSystemTemplate : `${reviewSystemTemplate.trim()}
120938
121549
 
@@ -120941,13 +121552,13 @@ ${reviewSecurity}`;
120941
121552
 
120942
121553
  ${reviewOutputContract}`;
120943
121554
  if (containsCompetingBehaviorStateMarkup(renderedReviewSystem)) {
120944
- throw new CriticalBehaviorStateError();
121555
+ throw new BehaviorMemoryUnavailableError();
120945
121556
  }
120946
121557
  } catch (error48) {
120947
- if (error48 instanceof CriticalBehaviorStateError) {
121558
+ if (error48 instanceof BehaviorMemoryUnavailableError) {
120948
121559
  throw error48;
120949
121560
  }
120950
- throw new CriticalBehaviorStateError();
121561
+ throw new BehaviorMemoryUnavailableError(error48);
120951
121562
  }
120952
121563
  };
120953
121564
  extractRuntimeReasoningSelection = (settings, controlType, toggleBehavior = "disable_reasoning") => {
@@ -121034,7 +121645,7 @@ ${reviewOutputContract}`;
121034
121645
  return REVIEW_FAILURE_SQL_STATEMENT_PATTERN.test(lowered) && REVIEW_FAILURE_SCHEMA_DISCLOSURE_TOKENS.some((token) => lowered.includes(token));
121035
121646
  };
121036
121647
  summarizeReviewFailureExplanation = (detail) => {
121037
- const message = String(detail ?? "").trim();
121648
+ const message = sanitizeRuntimeDiagnosticValue(String(detail ?? "")).trim();
121038
121649
  if (!message) {
121039
121650
  return "The review step stopped before VTX received error details.";
121040
121651
  }
@@ -121932,33 +122543,11 @@ ${reviewOutputContract}`;
121932
122543
  ].join("\n");
121933
122544
  buildPromptPositionsValue = (input) => {
121934
122545
  const validateInstructionTemplate = (template, allowedKeys) => {
121935
- const escapedOpen = "__VTX_ESCAPED_OPEN__";
121936
- const escapedClose = "__VTX_ESCAPED_CLOSE__";
121937
- const normalizedTemplate = template.replace(/\{\{/g, escapedOpen).replace(/\}\}/g, escapedClose);
121938
- const formatted = normalizedTemplate.replace(/\{([a-z_]+)\}/g, (_match, key) => {
121939
- if (!allowedKeys.includes(key)) {
121940
- throw new Error(`Unexpected positions instruction placeholder: ${key}`);
121941
- }
121942
- return "";
121943
- });
121944
- if (/[{}]/.test(formatted)) {
121945
- throw new Error(`Invalid positions instruction template: ${template}`);
121946
- }
121947
- };
121948
- const formatInstructionTemplate2 = (template, values) => {
121949
- const escapedOpen = "__VTX_ESCAPED_OPEN__";
121950
- const escapedClose = "__VTX_ESCAPED_CLOSE__";
121951
- const normalizedTemplate = template.replace(/\{\{/g, escapedOpen).replace(/\}\}/g, escapedClose);
121952
- const formatted = normalizedTemplate.replace(/\{([a-z_]+)\}/g, (_match, key) => {
121953
- if (!Object.prototype.hasOwnProperty.call(values, key)) {
121954
- throw new Error(`Unexpected positions instruction placeholder: ${key}`);
121955
- }
121956
- return String(values[key]);
121957
- });
121958
- if (/[{}]/.test(formatted)) {
121959
- throw new Error(`Invalid positions instruction template: ${template}`);
121960
- }
121961
- return formatted.replaceAll(escapedOpen, "{").replaceAll(escapedClose, "}");
122546
+ formatInstructionTemplate(
122547
+ template,
122548
+ Object.fromEntries(allowedKeys.map((key) => [key, ""])),
122549
+ "positions instruction template"
122550
+ );
121962
122551
  };
121963
122552
  validateInstructionTemplate(input.positionsInstructions.close_reduce, []);
121964
122553
  validateInstructionTemplate(input.positionsInstructions.capacity_flat, []);
@@ -122053,9 +122642,9 @@ ${reviewOutputContract}`;
122053
122642
  if (remainingGlobal <= 0) {
122054
122643
  parts.push(`${input.positionsInstructions.capacity_full} `);
122055
122644
  } else if (input.maxTradesPerPrompt < input.maxTradesGlobal && remainingGlobal < input.maxTradesPerPrompt) {
122056
- parts.push(`${formatInstructionTemplate2(input.positionsInstructions.capacity_low, {
122645
+ parts.push(`${formatInstructionTemplate(input.positionsInstructions.capacity_low, {
122057
122646
  remaining: remainingGlobal
122058
- })} `);
122647
+ }, "positions instruction template")} `);
122059
122648
  }
122060
122649
  return parts.join("\n");
122061
122650
  };
@@ -122551,6 +123140,9 @@ ${reviewOutputContract}`;
122551
123140
  const matches2 = Array.from(
122552
123141
  userPrompt.matchAll(/<behavior_state>\s*([\s\S]*?)\s*<\/behavior_state>/g)
122553
123142
  );
123143
+ if (openingTags.length === 0 && closingTags.length === 0) {
123144
+ throw new BehaviorMemoryUnavailableError();
123145
+ }
122554
123146
  if (openingTags.length !== 1 || closingTags.length !== 1 || matches2.length !== 1) {
122555
123147
  throw new CriticalBehaviorStateError();
122556
123148
  }
@@ -123533,27 +124125,6 @@ ${behaviorJson}
123533
124125
  }
123534
124126
  }
123535
124127
  };
123536
- formatTemplateWithNamedVariables = (template, values) => {
123537
- const escapedOpen = "__VTX_FMT_OPEN__";
123538
- const escapedClose = "__VTX_FMT_CLOSE__";
123539
- const prepared = String(template || "").replaceAll("{{", escapedOpen).replaceAll("}}", escapedClose);
123540
- const validatedTemplate = prepared.replace(/\{([a-zA-Z_][a-zA-Z0-9_]*)\}/g, (_match, key) => {
123541
- if (!Object.prototype.hasOwnProperty.call(values, key)) {
123542
- throw new Error(`Missing required review template variable: ${key}`);
123543
- }
123544
- return "";
123545
- });
123546
- if (/[{}]/.test(validatedTemplate)) {
123547
- throw new Error(`Invalid review template: ${template}`);
123548
- }
123549
- const formatted = prepared.replace(/\{([a-zA-Z_][a-zA-Z0-9_]*)\}/g, (_match, key) => {
123550
- if (!Object.prototype.hasOwnProperty.call(values, key)) {
123551
- throw new Error(`Missing required review template variable: ${key}`);
123552
- }
123553
- return String(values[key]);
123554
- });
123555
- return formatted.replaceAll(escapedOpen, "{").replaceAll(escapedClose, "}");
123556
- };
123557
124128
  carryReturnedModelCalls = (error48, attempts) => {
123558
124129
  if (!attempts.length || !error48 || typeof error48 !== "object" && typeof error48 !== "function") return error48;
123559
124130
  error48.runtimeReturnedModelCalls = attempts;
@@ -125291,7 +125862,7 @@ ${stringifyPromptJson(candlesPayload)}
125291
125862
  reviewInstructions.review_security,
125292
125863
  "review_instructions.review_security"
125293
125864
  );
125294
- const reviewOutputContract = formatTemplateWithNamedVariables(
125865
+ const reviewOutputContract = formatInstructionTemplate(
125295
125866
  reviewOutputFormat,
125296
125867
  buildDecisionInstructionVariables(reviewSymbols, reviewMaxTrades)
125297
125868
  );
@@ -125314,12 +125885,18 @@ ${reviewOutputContract}`;
125314
125885
  configuredReviewUserTemplate
125315
125886
  ) : configuredReviewUserTemplate;
125316
125887
  const renderedPrimaryUserPrompt = stringifyPromptJson(userPrompt);
125317
- const reviewUserPrompt = formatTemplateWithNamedVariables(reviewUserTemplate, {
125318
- primary_model: selectedPrimaryModel,
125319
- primary_system_prompt: stringifyPromptJson(systemPrompt),
125320
- primary_user_prompt: renderedPrimaryUserPrompt,
125321
- primary_decision_json: primaryDecisionJson
125322
- });
125888
+ let reviewUserPrompt;
125889
+ try {
125890
+ reviewUserPrompt = formatInstructionTemplate(reviewUserTemplate, {
125891
+ primary_model: selectedPrimaryModel,
125892
+ primary_system_prompt: stringifyPromptJson(systemPrompt),
125893
+ primary_user_prompt: renderedPrimaryUserPrompt,
125894
+ primary_decision_json: primaryDecisionJson
125895
+ });
125896
+ } catch (error48) {
125897
+ if (input.mode === "trader") throw new CriticalBehaviorStateError(error48);
125898
+ throw error48;
125899
+ }
125323
125900
  if (input.mode === "trader" && (reviewUserPrompt.split(renderedPrimaryUserPrompt).length - 1 !== 1 || /<\/?behavior_state\b/.test(reviewUserPrompt) || containsCompetingBehaviorStateMarkup(reviewSystemPrompt))) {
125324
125901
  throw new CriticalBehaviorStateError();
125325
125902
  }
@@ -126867,10 +127444,10 @@ var init_engine = __esm({
126867
127444
  outcome: "error"
126868
127445
  });
126869
127446
  await new Promise((resolve14) => {
126870
- let settled = false;
127447
+ let settled2 = false;
126871
127448
  const finish = () => {
126872
- if (settled) return;
126873
- settled = true;
127449
+ if (settled2) return;
127450
+ settled2 = true;
126874
127451
  globalThis.clearTimeout(timeoutId);
126875
127452
  signal.removeEventListener("abort", finish);
126876
127453
  resolve14();
@@ -127813,14 +128390,14 @@ var init_engine = __esm({
127813
128390
  const loop = this._executionLoopPromise;
127814
128391
  if (!loop) return true;
127815
128392
  let timer;
127816
- const settled = await Promise.race([
128393
+ const settled2 = await Promise.race([
127817
128394
  loop.then(() => true, () => true),
127818
128395
  new Promise((resolve14) => {
127819
128396
  timer = setTimeout(() => resolve14(false), timeoutMs);
127820
128397
  })
127821
128398
  ]);
127822
128399
  clearTimeout(timer);
127823
- return settled;
128400
+ return settled2;
127824
128401
  }
127825
128402
  get active() {
127826
128403
  return this._startPromise !== null || this._isStopping || this._state === "running" || this._state === "stale" || this._state === "offline";
@@ -128111,6 +128688,7 @@ var init_engine = __esm({
128111
128688
  const runtime = await this.notifyRuntimeStop(this._profileId, {
128112
128689
  keepalive: options?.keepalive === true,
128113
128690
  reason: stopReason,
128691
+ modeSwitch: options?.modeSwitch === true,
128114
128692
  killswitchTrigger: options?.killswitchTrigger ?? null,
128115
128693
  authoritativeIntent: this._remoteStopPending === "authoritative-stop" && this._pendingAuthoritativeStopDetails?.authoritativeIntent === true
128116
128694
  });
@@ -128190,7 +128768,8 @@ var init_engine = __esm({
128190
128768
  reason: effectiveRemoteStopReason,
128191
128769
  killswitchTrigger: supersedingStop?.killswitchTrigger ?? options?.killswitchTrigger ?? null,
128192
128770
  acceptDeferredStopCompletion: !remoteStopWasAuthoritativeAtDispatch,
128193
- authoritativeIntent: supersedingStop?.authoritativeIntent === true
128771
+ authoritativeIntent: supersedingStop?.authoritativeIntent === true,
128772
+ modeSwitch: !supersedingStop && options?.modeSwitch === true
128194
128773
  });
128195
128774
  this._setRuntimeStatus(runtime, "stop");
128196
128775
  appendRuntimeDebugEvent({
@@ -128949,10 +129528,10 @@ var init_engine = __esm({
128949
129528
  throw signal.reason ?? createStopAbortError("trade_sync_settlement_cancelled");
128950
129529
  }
128951
129530
  await new Promise((resolve14) => {
128952
- let settled = false;
129531
+ let settled2 = false;
128953
129532
  const finish = () => {
128954
- if (settled) return;
128955
- settled = true;
129533
+ if (settled2) return;
129534
+ settled2 = true;
128956
129535
  globalThis.clearTimeout(timeoutId);
128957
129536
  signal?.removeEventListener("abort", finish);
128958
129537
  resolve14();
@@ -129573,7 +130152,9 @@ var init_engine = __esm({
129573
130152
  reviewModelResponse: result.reviewModelResponse,
129574
130153
  primaryReasoningContent: result.primaryReasoningContent,
129575
130154
  reviewReasoningContent: result.reviewReasoningContent,
129576
- reviewFailureReason: result.reviewFailureReason,
130155
+ // Raw provider error text never leaves the device; the server
130156
+ // stores the reason through the same redaction contract.
130157
+ reviewFailureReason: result.reviewFailureReason == null ? result.reviewFailureReason : sanitizeRuntimeDiagnosticValue(result.reviewFailureReason),
129577
130158
  systemPrompt: result.systemPrompt,
129578
130159
  userPrompt: result.userPrompt,
129579
130160
  reviewSystemPrompt: result.reviewSystemPrompt,
@@ -131735,7 +132316,8 @@ var init_engine = __esm({
131735
132316
  lastRunAt: this._lastRunAt,
131736
132317
  stopReason: options?.reason ?? null,
131737
132318
  killswitchTrigger: options?.killswitchTrigger ?? null,
131738
- authoritativeIntent: options?.authoritativeIntent === true
132319
+ authoritativeIntent: options?.authoritativeIntent === true,
132320
+ modeSwitch: options?.modeSwitch === true
131739
132321
  },
131740
132322
  {
131741
132323
  ...options,