claude-use 11.8.1 → 11.9.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/cli.cjs CHANGED
@@ -26886,9 +26886,15 @@ function expandAllCategoryKey(pairs) {
26886
26886
  const expanded = Object.fromEntries(OVERRIDABLE_CATEGORIES.filter((category) => !all2 || category !== "runtime").map((category) => [category, all2]));
26887
26887
  return { ...expanded, ...rest };
26888
26888
  }
26889
+ function isHttpProvider(provider) {
26890
+ return provider.kind === void 0 || provider.kind === "http";
26891
+ }
26889
26892
  function isCodexProvider(provider) {
26890
26893
  return provider.kind === "codex";
26891
26894
  }
26895
+ function isAntigravityProvider(provider) {
26896
+ return provider.kind === "antigravity";
26897
+ }
26892
26898
  function poolMemberIdentity(member) {
26893
26899
  return typeof member === "string" ? member : member.identity;
26894
26900
  }
@@ -26900,7 +26906,7 @@ function isTimeZone(name) {
26900
26906
  return false;
26901
26907
  }
26902
26908
  }
26903
- var import_node_path4, CATEGORY_NAMES, OVERRIDABLE_CATEGORIES, CategoryMapSchema, DURATION_RE, DurationSchema, WhenConditionObjectSchema, WhenSchema, EntryValueSchema, ENTRY_KEY_RE, EntriesSchema, LaunchSchema, CREDENTIAL_TARGETS, PROVIDER_CREDENTIAL_TARGETS, CREDENTIAL_TARGET_VARS, ArgvSchema, CommandSourceOptions, EnvCredentialSourceSchema, FileCredentialSourceSchema, CommandCredentialSourceSchema, OpCredentialSourceSchema, KeychainCredentialSourceSchema, LiteralCredentialSourceSchema, CredentialSourceSchema, RemoteCredentialSourceSchema, CREDENTIAL_CACHE_STORES, CredentialCacheSchema, CredentialSchema, ProviderCredentialSchema, RESERVED_PROVIDER_ENV_KEYS, ProviderEnvSchema, PROVIDER_KINDS, CODEX_TIERS, CODEX_EFFORTS, CODEX_LOGINS, CODEX_DEFAULT_LOGIN, CODEX_DEFAULT_MODEL, CODEX_DEFAULT_TIER_MODELS, CODEX_DEFAULT_EFFORT, CodexProviderConfigSchema, ProviderRouteSchema, HttpProviderSchema, CodexProviderSchema, ProviderSchema, ConfigProfileSchema, POOL_SELECTOR_PREFIX, POOL_NAME_PATTERN, IDENTITY_NAME_PATTERN, PoolNameSchema, SELECTOR_RE, IdentitySelectorSchema, PoolMemberSchema, POOL_PREFERENCES, PoolPreferenceSchema, PoolSchema, WEEKDAYS, AnchorSchema, JOB_WINDOWS, JobTriggerSchema, JobTargetSchema, JobSchema, DirectoryRuleSchema, DirectoryRulesSchema, PortableConfigSchema, HEADROOM_MODES, HEADROOM_CCR_MODES, HEADROOM_ROLLOUT_CHANNELS, INTERCEPT_CHANNELS, READ_MATURATION_CHANNELS, HeadroomGlobalConfigObjectSchema, HeadroomGlobalConfigSchema, HEADROOM_DEFAULT_SOURCE, HEADROOM_DEFAULT_IDLE_SHUTDOWN_MINUTES, FRONTDOOR_DEFAULT_IDLE_SHUTDOWN_MINUTES, FrontDoorGlobalConfigSchema, UPDATE_MODES, UpdateGlobalConfigSchema, GlobalConfigSchema, IdentitySchema, CategoryClassificationSchema, CategoryClassificationOverlaySchema, SHIPPED_CATEGORY_DEFAULTS;
26909
+ var import_node_path4, CATEGORY_NAMES, OVERRIDABLE_CATEGORIES, CategoryMapSchema, DURATION_RE, DurationSchema, WhenConditionObjectSchema, WhenSchema, EntryValueSchema, ENTRY_KEY_RE, EntriesSchema, LaunchSchema, CREDENTIAL_TARGETS, PROVIDER_CREDENTIAL_TARGETS, CREDENTIAL_TARGET_VARS, ArgvSchema, CommandSourceOptions, EnvCredentialSourceSchema, FileCredentialSourceSchema, CommandCredentialSourceSchema, OpCredentialSourceSchema, KeychainCredentialSourceSchema, LiteralCredentialSourceSchema, CredentialSourceSchema, RemoteCredentialSourceSchema, CREDENTIAL_CACHE_STORES, CredentialCacheSchema, CredentialSchema, ProviderCredentialSchema, RESERVED_PROVIDER_ENV_KEYS, ProviderEnvSchema, PROVIDER_KINDS, ANTIGRAVITY_MODES, ANTIGRAVITY_TIERS, ANTIGRAVITY_EFFORTS, ANTIGRAVITY_DEFAULT_MODE, ANTIGRAVITY_DEFAULT_MODEL, ANTIGRAVITY_DEFAULT_TIER_MODELS, ANTIGRAVITY_DEFAULT_EFFORT, AntigravityProviderConfigSchema, CODEX_TIERS, CODEX_EFFORTS, CODEX_LOGINS, CODEX_DEFAULT_LOGIN, CODEX_DEFAULT_MODEL, CODEX_DEFAULT_TIER_MODELS, CODEX_DEFAULT_EFFORT, CodexProviderConfigSchema, ProviderRouteSchema, HttpProviderSchema, CodexProviderSchema, AntigravityProviderSchema, ProviderSchema, ConfigProfileSchema, POOL_SELECTOR_PREFIX, POOL_NAME_PATTERN, IDENTITY_NAME_PATTERN, PoolNameSchema, SELECTOR_RE, IdentitySelectorSchema, PoolMemberSchema, POOL_PREFERENCES, PoolPreferenceSchema, PoolSchema, WEEKDAYS, AnchorSchema, JOB_WINDOWS, JobTriggerSchema, JobTargetSchema, JobSchema, DirectoryRuleSchema, DirectoryRulesSchema, PortableConfigSchema, HEADROOM_MODES, HEADROOM_CCR_MODES, HEADROOM_ROLLOUT_CHANNELS, INTERCEPT_CHANNELS, READ_MATURATION_CHANNELS, HeadroomGlobalConfigObjectSchema, HeadroomGlobalConfigSchema, HEADROOM_DEFAULT_SOURCE, HEADROOM_DEFAULT_IDLE_SHUTDOWN_MINUTES, FRONTDOOR_DEFAULT_IDLE_SHUTDOWN_MINUTES, FrontDoorGlobalConfigSchema, UPDATE_MODES, UpdateGlobalConfigSchema, GlobalConfigSchema, IdentitySchema, CategoryClassificationSchema, CategoryClassificationOverlaySchema, SHIPPED_CATEGORY_DEFAULTS;
26904
26910
  var init_schema = __esm({
26905
26911
  "src/config/schema.ts"() {
26906
26912
  "use strict";
@@ -26999,7 +27005,50 @@ var init_schema = __esm({
26999
27005
  ProviderEnvSchema = external_exports.record(external_exports.string().min(1), external_exports.string()).refine((env) => !Object.keys(env).some((key) => RESERVED_PROVIDER_ENV_KEYS.includes(key)), {
27000
27006
  message: `env may not set ${RESERVED_PROVIDER_ENV_KEYS.join(", ")}: the credential block's target sets one and agent-shim removes the others`
27001
27007
  });
27002
- PROVIDER_KINDS = ["http", "codex"];
27008
+ PROVIDER_KINDS = ["http", "codex", "antigravity"];
27009
+ ANTIGRAVITY_MODES = ["cloud", "local"];
27010
+ ANTIGRAVITY_TIERS = ["fable", "opus", "sonnet", "haiku"];
27011
+ ANTIGRAVITY_EFFORTS = ["none", "low", "medium", "high", "xhigh", "max"];
27012
+ ANTIGRAVITY_DEFAULT_MODE = "cloud";
27013
+ ANTIGRAVITY_DEFAULT_MODEL = "gemini-2.5-pro";
27014
+ ANTIGRAVITY_DEFAULT_TIER_MODELS = Object.freeze({
27015
+ fable: "gemini-2.5-pro",
27016
+ opus: "gemini-2.5-pro",
27017
+ sonnet: "gemini-2.5-flash",
27018
+ haiku: "gemini-2.5-flash"
27019
+ });
27020
+ ANTIGRAVITY_DEFAULT_EFFORT = "low";
27021
+ AntigravityProviderConfigSchema = external_exports.strictObject({
27022
+ /** Operational mode: direct cloud endpoint or local ACP daemon. Defaults to `cloud`. */
27023
+ mode: external_exports.enum(ANTIGRAVITY_MODES).optional(),
27024
+ /** The model a request maps to when no tier matches its model name. */
27025
+ defaultModel: external_exports.string().min(1).optional(),
27026
+ /** Per-tier overrides of the shipped mapping, matched by substring of the requested model name in `ANTIGRAVITY_TIERS` order. */
27027
+ models: external_exports.strictObject({
27028
+ fable: external_exports.string().min(1).optional(),
27029
+ opus: external_exports.string().min(1).optional(),
27030
+ sonnet: external_exports.string().min(1).optional(),
27031
+ haiku: external_exports.string().min(1).optional()
27032
+ }).optional(),
27033
+ /** The reasoning effort used when the request's own effort is not one the backend accepts. */
27034
+ effort: external_exports.enum(ANTIGRAVITY_EFFORTS).optional(),
27035
+ /** Cloud-specific settings (for `mode: "cloud"`). */
27036
+ cloud: external_exports.strictObject({
27037
+ /** Google Gemini API or custom gateway endpoint. Defaults to `https://generativelanguage.googleapis.com`. */
27038
+ endpoint: external_exports.url().optional(),
27039
+ /** Google Cloud Project ID (when using Vertex AI). */
27040
+ projectId: external_exports.string().min(1).optional(),
27041
+ /** Google Cloud location/region (when using Vertex AI). */
27042
+ location: external_exports.string().min(1).optional()
27043
+ }).optional(),
27044
+ /** Local-specific settings (for `mode: "local"`). */
27045
+ local: external_exports.strictObject({
27046
+ /** Command and arguments to spawn the ACP server process. */
27047
+ command: external_exports.array(external_exports.string().min(1)).min(1).optional(),
27048
+ /** Path to an existing Unix domain socket to connect to instead of spawning a process. */
27049
+ socketPath: external_exports.string().min(1).optional()
27050
+ }).optional()
27051
+ });
27003
27052
  CODEX_TIERS = ["fable", "opus", "sonnet", "haiku"];
27004
27053
  CODEX_EFFORTS = ["none", "low", "medium", "high"];
27005
27054
  CODEX_LOGINS = ["codex-cli", "chatgpt-sign-in"];
@@ -27053,7 +27102,15 @@ var init_schema = __esm({
27053
27102
  env: ProviderEnvSchema.optional(),
27054
27103
  codex: CodexProviderConfigSchema.optional()
27055
27104
  });
27056
- ProviderSchema = external_exports.discriminatedUnion("kind", [HttpProviderSchema, CodexProviderSchema]);
27105
+ AntigravityProviderSchema = external_exports.strictObject({
27106
+ $schema: external_exports.string().optional(),
27107
+ kind: external_exports.literal("antigravity"),
27108
+ displayName: external_exports.string().min(1),
27109
+ credential: ProviderCredentialSchema,
27110
+ env: ProviderEnvSchema.optional(),
27111
+ antigravity: AntigravityProviderConfigSchema.optional()
27112
+ });
27113
+ ProviderSchema = external_exports.discriminatedUnion("kind", [HttpProviderSchema, CodexProviderSchema, AntigravityProviderSchema]);
27057
27114
  ConfigProfileSchema = external_exports.strictObject({
27058
27115
  $schema: external_exports.string().optional(),
27059
27116
  description: external_exports.string().optional(),
@@ -27616,7 +27673,7 @@ function daemonIdentity(commandLine, socketPath) {
27616
27673
  function earlierReleaseAllowlistHash(providers, doorOrigin) {
27617
27674
  const entries = /* @__PURE__ */ new Set([EARLIER_RELEASE_ANTHROPIC_UPSTREAM]);
27618
27675
  for (const provider of providers) {
27619
- if (!isCodexProvider(provider)) {
27676
+ if (isHttpProvider(provider)) {
27620
27677
  entries.add(provider.baseUrl);
27621
27678
  }
27622
27679
  }
@@ -34007,7 +34064,7 @@ var init_package = __esm({
34007
34064
  "package.json"() {
34008
34065
  package_default = {
34009
34066
  name: "claude-use",
34010
- version: "11.8.1",
34067
+ version: "11.9.0",
34011
34068
  description: "A profile manager and launcher for Claude Code that lets one person run multiple logins from one machine while controlling what gets shared between them.",
34012
34069
  license: "MIT",
34013
34070
  author: "Joseph Mearman <joseph@mearman.co.uk>",
@@ -35669,11 +35726,20 @@ function listProviderNames(readdir, providersDir) {
35669
35726
  return entries.filter((entry) => entry.endsWith(".json")).map((entry) => entry.slice(0, -".json".length)).sort();
35670
35727
  }
35671
35728
  function describeProviderEndpoint(provider) {
35672
- return isCodexProvider(provider) ? "codex translation daemon" : provider.baseUrl;
35729
+ if (isCodexProvider(provider)) {
35730
+ return "codex translation daemon";
35731
+ }
35732
+ if (isAntigravityProvider(provider)) {
35733
+ return (provider.antigravity?.mode ?? ANTIGRAVITY_DEFAULT_MODE) === "local" ? "antigravity local (ACP daemon)" : "antigravity cloud (Gemini API)";
35734
+ }
35735
+ return provider.baseUrl;
35673
35736
  }
35674
35737
  function isEmptyCodexConfig(config2) {
35675
35738
  return config2 === void 0 || config2.defaultModel === void 0 && config2.effort === void 0 && config2.login === void 0 && (config2.models === void 0 || Object.keys(config2.models).length === 0);
35676
35739
  }
35740
+ function isEmptyAntigravityConfig(config2) {
35741
+ return config2 === void 0 || config2.mode === void 0 && config2.defaultModel === void 0 && config2.effort === void 0 && config2.cloud === void 0 && config2.local === void 0 && (config2.models === void 0 || Object.keys(config2.models).length === 0);
35742
+ }
35677
35743
  function addProvider(paths, name, input2) {
35678
35744
  if (providerExists(paths, name)) {
35679
35745
  throw new ProviderAlreadyExistsError(name);
@@ -35685,19 +35751,25 @@ function addProvider(paths, name, input2) {
35685
35751
  if (kind === "codex" && input2.baseUrl !== void 0) {
35686
35752
  throw new ProviderKindMismatchError("A codex provider has no base URL: the launcher points its sessions at the front-door daemon. Drop --base-url.");
35687
35753
  }
35754
+ if (kind === "antigravity" && input2.baseUrl !== void 0) {
35755
+ throw new ProviderKindMismatchError("An antigravity provider has no base URL: the launcher points its sessions at the front-door daemon. Drop --base-url.");
35756
+ }
35688
35757
  if (kind === "http" && input2.baseUrl === void 0) {
35689
35758
  throw new ProviderKindMismatchError("An http provider needs --base-url.");
35690
35759
  }
35691
- if (kind === "http" && !isEmptyCodexConfig(input2.codex)) {
35760
+ if (kind !== "codex" && !isEmptyCodexConfig(input2.codex)) {
35692
35761
  throw new ProviderKindMismatchError("Codex settings apply only to a codex provider (--kind codex).");
35693
35762
  }
35763
+ if (kind !== "antigravity" && !isEmptyAntigravityConfig(input2.antigravity)) {
35764
+ throw new ProviderKindMismatchError("Antigravity settings apply only to an antigravity provider (--kind antigravity).");
35765
+ }
35694
35766
  const shared = {
35695
35767
  displayName: input2.displayName,
35696
35768
  credential: { sources: input2.sources, ...input2.target === void 0 ? {} : { target: input2.target } },
35697
35769
  ...input2.env === void 0 || Object.keys(input2.env).length === 0 ? {} : { env: input2.env }
35698
35770
  };
35699
35771
  const parsed = ProviderSchema.safeParse(
35700
- kind === "codex" ? { kind, ...shared, ...isEmptyCodexConfig(input2.codex) ? {} : { codex: input2.codex } } : { ...shared, baseUrl: input2.baseUrl }
35772
+ kind === "codex" ? { kind, ...shared, ...isEmptyCodexConfig(input2.codex) ? {} : { codex: input2.codex } } : kind === "antigravity" ? { kind, ...shared, ...isEmptyAntigravityConfig(input2.antigravity) ? {} : { antigravity: input2.antigravity } } : { ...shared, baseUrl: input2.baseUrl }
35701
35773
  );
35702
35774
  if (!parsed.success) {
35703
35775
  throw new ConfigValidationError(providerJsonPath(paths, name), parsed.error.issues);
@@ -35717,8 +35789,14 @@ function updateProvider(paths, name, input2) {
35717
35789
  if (isCodexProvider(existing) && input2.baseUrl !== void 0) {
35718
35790
  throw new ProviderKindMismatchError(`Provider "${name}" is a codex provider, which has no base URL.`);
35719
35791
  }
35792
+ if (isAntigravityProvider(existing) && input2.baseUrl !== void 0) {
35793
+ throw new ProviderKindMismatchError(`Provider "${name}" is an antigravity provider, which has no base URL.`);
35794
+ }
35720
35795
  if (!isCodexProvider(existing) && !isEmptyCodexConfig(input2.codex)) {
35721
- throw new ProviderKindMismatchError(`Provider "${name}" is an http provider; codex settings apply only to a codex provider.`);
35796
+ throw new ProviderKindMismatchError(`Provider "${name}" is not a codex provider; codex settings apply only to a codex provider.`);
35797
+ }
35798
+ if (!isAntigravityProvider(existing) && !isEmptyAntigravityConfig(input2.antigravity)) {
35799
+ throw new ProviderKindMismatchError(`Provider "${name}" is not an antigravity provider; antigravity settings apply only to an antigravity provider.`);
35722
35800
  }
35723
35801
  const shared = {
35724
35802
  ...input2.displayName === void 0 ? {} : { displayName: input2.displayName },
@@ -35737,6 +35815,13 @@ function updateProvider(paths, name, input2) {
35737
35815
  ...existing.codex?.models === void 0 && input2.codex?.models === void 0 ? {} : { models: { ...existing.codex?.models, ...input2.codex?.models } }
35738
35816
  };
35739
35817
  candidate = { ...existing, ...shared, codex: isEmptyCodexConfig(codex) ? void 0 : codex };
35818
+ } else if (isAntigravityProvider(existing)) {
35819
+ const antigravity = {
35820
+ ...existing.antigravity,
35821
+ ...input2.antigravity,
35822
+ ...existing.antigravity?.models === void 0 && input2.antigravity?.models === void 0 ? {} : { models: { ...existing.antigravity?.models, ...input2.antigravity?.models } }
35823
+ };
35824
+ candidate = { ...existing, ...shared, antigravity: isEmptyAntigravityConfig(antigravity) ? void 0 : antigravity };
35740
35825
  } else {
35741
35826
  candidate = { ...existing, ...shared, ...input2.baseUrl === void 0 ? {} : { baseUrl: input2.baseUrl } };
35742
35827
  }
@@ -36974,7 +37059,7 @@ var require_util2 = __commonJS({
36974
37059
  var { kDestroyed, kBodyUsed, kListeners, kBody } = require_symbols();
36975
37060
  var { IncomingMessage: IncomingMessage2 } = require("node:http");
36976
37061
  var stream = require("node:stream");
36977
- var net4 = require("node:net");
37062
+ var net5 = require("node:net");
36978
37063
  var { stringify } = require("node:querystring");
36979
37064
  var { EventEmitter: EE2 } = require("node:events");
36980
37065
  var timers = require_timers();
@@ -37123,7 +37208,7 @@ var require_util2 = __commonJS({
37123
37208
  }
37124
37209
  assert2(typeof host === "string");
37125
37210
  const servername = getHostname(host);
37126
- if (net4.isIP(servername)) {
37211
+ if (net5.isIP(servername)) {
37127
37212
  return "";
37128
37213
  }
37129
37214
  return servername;
@@ -38786,7 +38871,7 @@ var require_dispatcher_base = __commonJS({
38786
38871
  var require_connect = __commonJS({
38787
38872
  "node_modules/.pnpm/undici@7.29.1/node_modules/undici/lib/core/connect.js"(exports2, module2) {
38788
38873
  "use strict";
38789
- var net4 = require("node:net");
38874
+ var net5 = require("node:net");
38790
38875
  var assert2 = require("node:assert");
38791
38876
  var util2 = require_util2();
38792
38877
  var { InvalidArgumentError: InvalidArgumentError2 } = require_errors();
@@ -38869,7 +38954,7 @@ var require_connect = __commonJS({
38869
38954
  } else {
38870
38955
  assert2(!httpSocket, "httpSocket can only be sent on TLS update");
38871
38956
  port = port || 80;
38872
- socket = net4.connect({
38957
+ socket = net5.connect({
38873
38958
  highWaterMark: 64 * 1024,
38874
38959
  // Same as nodejs fs streams.
38875
38960
  ...options,
@@ -44546,7 +44631,7 @@ var require_client = __commonJS({
44546
44631
  "node_modules/.pnpm/undici@7.29.1/node_modules/undici/lib/dispatcher/client.js"(exports2, module2) {
44547
44632
  "use strict";
44548
44633
  var assert2 = require("node:assert");
44549
- var net4 = require("node:net");
44634
+ var net5 = require("node:net");
44550
44635
  var http8 = require("node:http");
44551
44636
  var util2 = require_util2();
44552
44637
  var { ClientStats } = require_stats();
@@ -44701,7 +44786,7 @@ var require_client = __commonJS({
44701
44786
  if (maxRequestsPerClient != null && (!Number.isInteger(maxRequestsPerClient) || maxRequestsPerClient < 0)) {
44702
44787
  throw new InvalidArgumentError2("maxRequestsPerClient must be a positive number");
44703
44788
  }
44704
- if (localAddress != null && (typeof localAddress !== "string" || net4.isIP(localAddress) === 0)) {
44789
+ if (localAddress != null && (typeof localAddress !== "string" || net5.isIP(localAddress) === 0)) {
44705
44790
  throw new InvalidArgumentError2("localAddress must be valid string IP address");
44706
44791
  }
44707
44792
  if (maxResponseSize != null && (!Number.isInteger(maxResponseSize) || maxResponseSize < -1)) {
@@ -44881,7 +44966,7 @@ var require_client = __commonJS({
44881
44966
  const idx = hostname3.indexOf("]");
44882
44967
  assert2(idx !== -1);
44883
44968
  const ip2 = hostname3.substring(1, idx);
44884
- assert2(net4.isIPv6(ip2));
44969
+ assert2(net5.isIPv6(ip2));
44885
44970
  hostname3 = ip2;
44886
44971
  }
44887
44972
  client[kConnecting] = true;
@@ -45826,10 +45911,10 @@ var require_socks5_utils = __commonJS({
45826
45911
  "node_modules/.pnpm/undici@7.29.1/node_modules/undici/lib/core/socks5-utils.js"(exports2, module2) {
45827
45912
  "use strict";
45828
45913
  var { Buffer: Buffer3 } = require("node:buffer");
45829
- var net4 = require("node:net");
45914
+ var net5 = require("node:net");
45830
45915
  var { InvalidArgumentError: InvalidArgumentError2 } = require_errors();
45831
45916
  function parseAddress(address) {
45832
- if (net4.isIPv4(address)) {
45917
+ if (net5.isIPv4(address)) {
45833
45918
  const parts = address.split(".").map(Number);
45834
45919
  return {
45835
45920
  type: 1,
@@ -45837,7 +45922,7 @@ var require_socks5_utils = __commonJS({
45837
45922
  buffer: Buffer3.from(parts)
45838
45923
  };
45839
45924
  }
45840
- if (net4.isIPv6(address)) {
45925
+ if (net5.isIPv6(address)) {
45841
45926
  return {
45842
45927
  type: 4,
45843
45928
  // IPv6
@@ -45860,7 +45945,7 @@ var require_socks5_utils = __commonJS({
45860
45945
  if (address.includes(".")) {
45861
45946
  const lastColonIndex = address.lastIndexOf(":");
45862
45947
  const ipv4Part = address.slice(lastColonIndex + 1);
45863
- if (net4.isIPv4(ipv4Part)) {
45948
+ if (net5.isIPv4(ipv4Part)) {
45864
45949
  const octets = ipv4Part.split(".").map(Number);
45865
45950
  const high = (octets[0] << 8 | octets[1]).toString(16);
45866
45951
  const low = (octets[2] << 8 | octets[3]).toString(16);
@@ -63657,10 +63742,10 @@ function resolveLaunch(params) {
63657
63742
  environment
63658
63743
  };
63659
63744
  }
63660
- function runLaunchPlan(plan, spawn5) {
63745
+ function runLaunchPlan(plan, spawn6) {
63661
63746
  try {
63662
63747
  plan.markChildStarted();
63663
- const result = spawn5.spawnSync(plan.bin, plan.args, { stdio: "inherit", env: plan.env });
63748
+ const result = spawn6.spawnSync(plan.bin, plan.args, { stdio: "inherit", env: plan.env });
63664
63749
  if (result.error !== void 0) {
63665
63750
  throw result.error;
63666
63751
  }
@@ -64109,7 +64194,7 @@ function createQuotaRefresher(deps) {
64109
64194
  function createProviderLookup(ports) {
64110
64195
  return (name) => {
64111
64196
  const definition = loadProvider(ports.providersDir, name, ports.fs);
64112
- if (definition === void 0 || isCodexProvider(definition)) {
64197
+ if (definition === void 0 || !isHttpProvider(definition)) {
64113
64198
  return void 0;
64114
64199
  }
64115
64200
  return {
@@ -112410,7 +112495,7 @@ function writeUsageSnapshot(log, snapshot) {
112410
112495
  log(`usage snapshot write failed: ${error63 instanceof Error ? error63.message : String(error63)}`);
112411
112496
  }
112412
112497
  }
112413
- function createCodexRoutePorts(log, signInFile) {
112498
+ function createCodexRoutePorts(log, signInFile, options) {
112414
112499
  const agent = createUpstreamAgent();
112415
112500
  const upstreamFetch = createUpstreamFetch(agent);
112416
112501
  const tempSuffix = `${String(process.pid)}.${(0, import_node_crypto9.randomUUID)()}`;
@@ -112426,9 +112511,11 @@ function createCodexRoutePorts(log, signInFile) {
112426
112511
  "codex-cli": { fetch: upstreamFetch, auth, timers: realTimers, randomId: import_node_crypto9.randomUUID },
112427
112512
  "chatgpt-sign-in": { fetch: upstreamFetch, auth: signIn.auth, timers: realTimers, randomId: import_node_crypto9.randomUUID, target: RESPONSES_API_TARGET }
112428
112513
  },
112429
- writeUsageSnapshot: (snapshot) => {
112430
- writeUsageSnapshot(log, snapshot);
112431
- },
112514
+ ...options?.enableUsageSnapshot === true ? {
112515
+ writeUsageSnapshot: (snapshot) => {
112516
+ writeUsageSnapshot(log, snapshot);
112517
+ }
112518
+ } : {},
112432
112519
  now: () => Date.now(),
112433
112520
  log
112434
112521
  };
@@ -112559,7 +112646,7 @@ function registerCodexCommand(program2, deps) {
112559
112646
  }
112560
112647
 
112561
112648
  // src/frontdoor/commands.ts
112562
- var import_node_crypto21 = require("node:crypto");
112649
+ var import_node_crypto23 = require("node:crypto");
112563
112650
  var import_node_path51 = __toESM(require("node:path"), 1);
112564
112651
  var import_node_fs19 = __toESM(require("node:fs"), 1);
112565
112652
  init_commandDeps();
@@ -114184,6 +114271,13 @@ function watchedInstallEntry(resolvedOwnExecutablePath, siblingExists) {
114184
114271
  const sibling = import_node_path44.default.join(parsed.dir, `agent-shim${parsed.ext}`);
114185
114272
  return siblingExists(sibling) ? sibling : resolvedOwnExecutablePath;
114186
114273
  }
114274
+ var AWAIT_PID_POLL_MS = 50;
114275
+ async function awaitPidExit(pid, boundMs, ports) {
114276
+ const deadline = ports.now() + boundMs;
114277
+ while (ports.isRunning(pid) && ports.now() < deadline) {
114278
+ await ports.sleep(AWAIT_PID_POLL_MS);
114279
+ }
114280
+ }
114187
114281
  var FRONTDOOR_SUPERVISOR_STILL_RUNNING = -1;
114188
114282
  var FRONTDOOR_POLL_MS = 1e3;
114189
114283
  var MS_PER_MINUTE3 = 6e4;
@@ -125795,7 +125889,7 @@ function providerValue(name, provider) {
125795
125889
  name,
125796
125890
  kind: provider.kind ?? "http",
125797
125891
  displayName: provider.displayName,
125798
- ...isCodexProvider(provider) ? provider.codex === void 0 ? {} : { codex: provider.codex } : { baseUrl: provider.baseUrl },
125892
+ ...isCodexProvider(provider) ? provider.codex === void 0 ? {} : { codex: provider.codex } : isAntigravityProvider(provider) ? provider.antigravity === void 0 ? {} : { antigravity: provider.antigravity } : { baseUrl: provider.baseUrl },
125799
125893
  credential: summariseCredential(provider.credential),
125800
125894
  ...provider.env === void 0 ? {} : { env: provider.env }
125801
125895
  };
@@ -125974,7 +126068,7 @@ function createConfigApiRouter(deps) {
125974
126068
  throw new ProviderNotFoundError(input2.name);
125975
126069
  }
125976
126070
  const credential = input2.credential;
125977
- if (input2.baseUrl !== void 0 && !isCodexProvider(existing) && input2.baseUrl !== existing.baseUrl && credential?.sources === void 0) {
126071
+ if (input2.baseUrl !== void 0 && isHttpProvider(existing) && input2.baseUrl !== existing.baseUrl && credential?.sources === void 0) {
125978
126072
  throw new ORPCError("BAD_REQUEST", { message: `Changing the base URL of provider "${input2.name}" requires a credential block in the same call: the stored credential is not sent to a different endpoint.` });
125979
126073
  }
125980
126074
  const cache = credential?.cache === void 0 ? void 0 : mergeCredentialCache(credential.cache === false ? { enabled: false } : { ...credential.cache, enabled: true }, existing.credential.cache);
@@ -127434,6 +127528,198 @@ function translateRequest(body, config2) {
127434
127528
  return { request: request7, toolNames: names };
127435
127529
  }
127436
127530
 
127531
+ // src/antigravity/translate.ts
127532
+ var import_node_crypto20 = require("node:crypto");
127533
+ init_schema();
127534
+ function resolveAntigravityConfig(config2) {
127535
+ const overrides = config2?.models;
127536
+ return {
127537
+ mode: config2?.mode ?? ANTIGRAVITY_DEFAULT_MODE,
127538
+ defaultModel: config2?.defaultModel ?? ANTIGRAVITY_DEFAULT_MODEL,
127539
+ models: {
127540
+ fable: overrides?.fable ?? ANTIGRAVITY_DEFAULT_TIER_MODELS.fable,
127541
+ opus: overrides?.opus ?? ANTIGRAVITY_DEFAULT_TIER_MODELS.opus,
127542
+ sonnet: overrides?.sonnet ?? ANTIGRAVITY_DEFAULT_TIER_MODELS.sonnet,
127543
+ haiku: overrides?.haiku ?? ANTIGRAVITY_DEFAULT_TIER_MODELS.haiku
127544
+ },
127545
+ effort: config2?.effort ?? ANTIGRAVITY_DEFAULT_EFFORT,
127546
+ cloud: {
127547
+ endpoint: config2?.cloud?.endpoint,
127548
+ projectId: config2?.cloud?.projectId,
127549
+ location: config2?.cloud?.location
127550
+ },
127551
+ local: {
127552
+ command: config2?.local?.command,
127553
+ socketPath: config2?.local?.socketPath
127554
+ }
127555
+ };
127556
+ }
127557
+ function mapModel2(requested, config2) {
127558
+ if (requested.startsWith("gemini-") || requested.startsWith("antigravity-")) {
127559
+ return requested;
127560
+ }
127561
+ const lower = requested.toLowerCase();
127562
+ const tier = ANTIGRAVITY_TIERS.find((candidate) => lower.includes(candidate));
127563
+ return tier === void 0 ? config2.defaultModel : config2.models[tier];
127564
+ }
127565
+ var EFFORT_TO_BUDGET = {
127566
+ none: 0,
127567
+ low: 1024,
127568
+ medium: 4096,
127569
+ high: 8192,
127570
+ xhigh: 16384,
127571
+ max: 32768
127572
+ };
127573
+ function mapEffort2(request7, config2) {
127574
+ const requested = request7.output_config?.effort;
127575
+ const level = ANTIGRAVITY_EFFORTS.find((effort) => effort === requested) ?? config2.effort;
127576
+ const budget = EFFORT_TO_BUDGET[level];
127577
+ return budget > 0 ? budget : void 0;
127578
+ }
127579
+ var BILLING_HEADER_LINE2 = /^x-anthropic-billing-header:[^\n]*\n/;
127580
+ function systemToInstruction(system) {
127581
+ if (system === void 0) {
127582
+ return void 0;
127583
+ }
127584
+ const texts = typeof system === "string" ? [system] : system.filter(isTextBlock).map((b) => b.text);
127585
+ const combined = texts.join("\n").replace(BILLING_HEADER_LINE2, "").trim();
127586
+ return combined.length > 0 ? { parts: [{ text: combined }] } : void 0;
127587
+ }
127588
+ var ANTIGRAVITY_TOOL_NAME_LIMIT = 64;
127589
+ var TOOL_NAME_HASH_CHARS2 = 8;
127590
+ function shortToolName2(name, names) {
127591
+ const sanitized = name.replace(/[^a-zA-Z0-9_]/g, "_");
127592
+ if (sanitized === name && name.length <= ANTIGRAVITY_TOOL_NAME_LIMIT) {
127593
+ return name;
127594
+ }
127595
+ let result;
127596
+ if (sanitized.length <= ANTIGRAVITY_TOOL_NAME_LIMIT) {
127597
+ result = sanitized;
127598
+ } else {
127599
+ const hash2 = (0, import_node_crypto20.createHash)("sha256").update(name).digest("hex").slice(0, TOOL_NAME_HASH_CHARS2);
127600
+ const prefix = sanitized.slice(0, ANTIGRAVITY_TOOL_NAME_LIMIT - TOOL_NAME_HASH_CHARS2 - 1);
127601
+ result = `${prefix}_${hash2}`;
127602
+ }
127603
+ names.set(result, name);
127604
+ return result;
127605
+ }
127606
+ var NON_TEXT_TOOL_RESULT2 = "[non-text tool result omitted]";
127607
+ function flattenToolResult2(content) {
127608
+ if (content === void 0) {
127609
+ return "";
127610
+ }
127611
+ if (typeof content === "string") {
127612
+ return content;
127613
+ }
127614
+ return content.map((block2) => isTextBlock(block2) ? block2.text : NON_TEXT_TOOL_RESULT2).join("\n");
127615
+ }
127616
+ function systemReminder2(text2) {
127617
+ return `<system-reminder>
127618
+ ${text2}
127619
+ </system-reminder>`;
127620
+ }
127621
+ function turnBlocks2(message) {
127622
+ const blocks = typeof message.content === "string" ? [{ type: "text", text: message.content }] : message.content;
127623
+ if (message.role !== "system") {
127624
+ return blocks;
127625
+ }
127626
+ return blocks.map((block2) => isTextBlock(block2) ? { ...block2, text: systemReminder2(block2.text) } : block2);
127627
+ }
127628
+ function isRecord6(value2) {
127629
+ return typeof value2 === "object" && value2 !== null && !Array.isArray(value2);
127630
+ }
127631
+ function messagesToGeminiContents(messages, names, toolIdToName) {
127632
+ const contents = [];
127633
+ let pendingRole;
127634
+ let pendingParts = [];
127635
+ const flush = () => {
127636
+ if (pendingRole !== void 0 && pendingParts.length > 0) {
127637
+ contents.push({ role: pendingRole, parts: pendingParts });
127638
+ }
127639
+ pendingRole = void 0;
127640
+ pendingParts = [];
127641
+ };
127642
+ const ensureRole = (role) => {
127643
+ if (pendingRole !== role) {
127644
+ flush();
127645
+ pendingRole = role;
127646
+ }
127647
+ return pendingParts;
127648
+ };
127649
+ for (const message of messages) {
127650
+ const defaultRole = message.role === "assistant" ? "model" : "user";
127651
+ for (const block2 of turnBlocks2(message)) {
127652
+ if (isTextBlock(block2)) {
127653
+ if (block2.text.trim() === "") {
127654
+ continue;
127655
+ }
127656
+ ensureRole(defaultRole).push({ text: block2.text });
127657
+ } else if (isImageBlock(block2)) {
127658
+ const { source } = block2;
127659
+ if (source.type === "base64") {
127660
+ ensureRole("user").push({
127661
+ inlineData: {
127662
+ mimeType: source.media_type,
127663
+ data: source.data
127664
+ }
127665
+ });
127666
+ }
127667
+ } else if (isToolUseBlock(block2)) {
127668
+ const sanitizedName = shortToolName2(block2.name, names);
127669
+ toolIdToName.set(block2.id, sanitizedName);
127670
+ ensureRole("model").push({
127671
+ functionCall: {
127672
+ name: sanitizedName,
127673
+ args: isRecord6(block2.input) ? block2.input : {}
127674
+ }
127675
+ });
127676
+ } else if (isToolResultBlock(block2)) {
127677
+ const toolName = toolIdToName.get(block2.tool_use_id) ?? "unknown_tool";
127678
+ ensureRole("user").push({
127679
+ functionResponse: {
127680
+ name: toolName,
127681
+ response: { output: flattenToolResult2(block2.content) }
127682
+ }
127683
+ });
127684
+ }
127685
+ }
127686
+ }
127687
+ flush();
127688
+ return contents;
127689
+ }
127690
+ var EMPTY_SCHEMA = { type: "object", properties: {} };
127691
+ function mapTools2(tools, names) {
127692
+ if (tools === void 0 || tools.length === 0) {
127693
+ return void 0;
127694
+ }
127695
+ const declarations = tools.map((tool) => ({
127696
+ name: shortToolName2(tool.name, names),
127697
+ description: tool.description,
127698
+ parameters: tool.input_schema ?? EMPTY_SCHEMA
127699
+ }));
127700
+ return [{ functionDeclarations: declarations }];
127701
+ }
127702
+ function translateRequest2(request7, config2) {
127703
+ const toolNames = /* @__PURE__ */ new Map();
127704
+ const toolIdToName = /* @__PURE__ */ new Map();
127705
+ const model = mapModel2(request7.model ?? "", config2);
127706
+ const thinkingBudget = mapEffort2(request7, config2);
127707
+ const systemInstruction = systemToInstruction(request7.system);
127708
+ const contents = messagesToGeminiContents(request7.messages, toolNames, toolIdToName);
127709
+ const tools = mapTools2(request7.tools, toolNames);
127710
+ const req = {
127711
+ contents,
127712
+ ...systemInstruction === void 0 ? {} : { systemInstruction },
127713
+ ...tools === void 0 ? {} : { tools },
127714
+ ...thinkingBudget !== void 0 ? { generationConfig: { thinkingConfig: { thinkingBudget } } } : {}
127715
+ };
127716
+ return {
127717
+ model,
127718
+ request: req,
127719
+ toolNames
127720
+ };
127721
+ }
127722
+
127437
127723
  // src/frontdoor/providerRoute.ts
127438
127724
  init_credential();
127439
127725
  init_providersStore();
@@ -127836,9 +128122,11 @@ function createCodexRoute(ports) {
127836
128122
  return errorResponse(HTTP_STATUS.badGateway, `codex backend unreachable: ${describeError3(error63)}`);
127837
128123
  }
127838
128124
  const snapshot = (quotaError) => {
127839
- const built = buildUsageSnapshot(upstream.headers, quotaError, ports.now());
127840
- if (built !== void 0) {
127841
- ports.writeUsageSnapshot(built);
128125
+ if (ports.writeUsageSnapshot !== void 0) {
128126
+ const built = buildUsageSnapshot(upstream.headers, quotaError, ports.now());
128127
+ if (built !== void 0) {
128128
+ ports.writeUsageSnapshot(built);
128129
+ }
127842
128130
  }
127843
128131
  };
127844
128132
  if (!upstream.ok || upstream.body === null) {
@@ -128024,6 +128312,770 @@ function createCodexRouteMount(ports, upstreamBase, provider) {
128024
128312
  };
128025
128313
  }
128026
128314
 
128315
+ // src/antigravity/route.ts
128316
+ var import_node_crypto21 = require("node:crypto");
128317
+ init_route();
128318
+
128319
+ // src/antigravity/relay.ts
128320
+ function renderSseFrame2(frame) {
128321
+ return `event: ${frame.event}
128322
+ data: ${JSON.stringify(frame.data)}
128323
+
128324
+ `;
128325
+ }
128326
+ function createAntigravityRelay(params) {
128327
+ const messageId = params.fallbackId();
128328
+ let started = false;
128329
+ let activeBlockType;
128330
+ let currentBlockIndex = -1;
128331
+ let sawToolUse = false;
128332
+ let finished = false;
128333
+ let usage = {
128334
+ input_tokens: 0,
128335
+ cache_creation_input_tokens: 0,
128336
+ cache_read_input_tokens: 0,
128337
+ output_tokens: 0
128338
+ };
128339
+ const frames = [];
128340
+ const ensureStarted = () => {
128341
+ if (!started) {
128342
+ started = true;
128343
+ frames.push({
128344
+ event: "message_start",
128345
+ data: {
128346
+ type: "message_start",
128347
+ message: {
128348
+ id: messageId,
128349
+ type: "message",
128350
+ role: "assistant",
128351
+ model: params.requestedModel,
128352
+ content: [],
128353
+ stop_reason: null,
128354
+ stop_sequence: null,
128355
+ usage: { input_tokens: 0, output_tokens: 0 }
128356
+ }
128357
+ }
128358
+ });
128359
+ }
128360
+ };
128361
+ const closeActiveBlock = () => {
128362
+ if (activeBlockType !== void 0 && currentBlockIndex >= 0) {
128363
+ frames.push({
128364
+ event: "content_block_stop",
128365
+ data: {
128366
+ type: "content_block_stop",
128367
+ index: currentBlockIndex
128368
+ }
128369
+ });
128370
+ activeBlockType = void 0;
128371
+ }
128372
+ };
128373
+ const pushChunk = (chunk) => {
128374
+ frames.length = 0;
128375
+ ensureStarted();
128376
+ if (chunk.usageMetadata !== void 0) {
128377
+ usage = {
128378
+ input_tokens: chunk.usageMetadata.promptTokenCount ?? usage.input_tokens,
128379
+ cache_creation_input_tokens: 0,
128380
+ cache_read_input_tokens: 0,
128381
+ output_tokens: chunk.usageMetadata.candidatesTokenCount ?? usage.output_tokens
128382
+ };
128383
+ }
128384
+ const candidate = chunk.candidates?.[0];
128385
+ if (candidate?.content?.parts !== void 0) {
128386
+ for (const part of candidate.content.parts) {
128387
+ if ("text" in part && typeof part.text === "string" && part.text.length > 0) {
128388
+ if (activeBlockType !== "text") {
128389
+ closeActiveBlock();
128390
+ currentBlockIndex += 1;
128391
+ activeBlockType = "text";
128392
+ frames.push({
128393
+ event: "content_block_start",
128394
+ data: {
128395
+ type: "content_block_start",
128396
+ index: currentBlockIndex,
128397
+ content_block: { type: "text", text: "" }
128398
+ }
128399
+ });
128400
+ }
128401
+ frames.push({
128402
+ event: "content_block_delta",
128403
+ data: {
128404
+ type: "content_block_delta",
128405
+ index: currentBlockIndex,
128406
+ delta: { type: "text_delta", text: part.text }
128407
+ }
128408
+ });
128409
+ } else if ("functionCall" in part && part.functionCall !== void 0) {
128410
+ sawToolUse = true;
128411
+ closeActiveBlock();
128412
+ currentBlockIndex += 1;
128413
+ activeBlockType = "tool_use";
128414
+ const callName = part.functionCall.name;
128415
+ const originalName = params.toolNames.get(callName) ?? callName;
128416
+ const callId = params.fallbackId();
128417
+ frames.push({
128418
+ event: "content_block_start",
128419
+ data: {
128420
+ type: "content_block_start",
128421
+ index: currentBlockIndex,
128422
+ content_block: {
128423
+ type: "tool_use",
128424
+ id: callId,
128425
+ name: originalName,
128426
+ input: {}
128427
+ }
128428
+ }
128429
+ });
128430
+ const argsJson = JSON.stringify(part.functionCall.args);
128431
+ frames.push({
128432
+ event: "content_block_delta",
128433
+ data: {
128434
+ type: "content_block_delta",
128435
+ index: currentBlockIndex,
128436
+ delta: {
128437
+ type: "input_json_delta",
128438
+ partial_json: argsJson
128439
+ }
128440
+ }
128441
+ });
128442
+ closeActiveBlock();
128443
+ }
128444
+ }
128445
+ }
128446
+ if (candidate?.finishReason !== void 0) {
128447
+ const stopReason = sawToolUse ? "tool_use" : candidate.finishReason === "MAX_TOKENS" ? "max_tokens" : "end_turn";
128448
+ closeActiveBlock();
128449
+ frames.push({
128450
+ event: "message_delta",
128451
+ data: {
128452
+ type: "message_delta",
128453
+ delta: { stop_reason: stopReason, stop_sequence: null },
128454
+ usage
128455
+ }
128456
+ });
128457
+ frames.push({
128458
+ event: "message_stop",
128459
+ data: { type: "message_stop" }
128460
+ });
128461
+ finished = true;
128462
+ }
128463
+ return { frames: [...frames], done: finished };
128464
+ };
128465
+ const finish = () => {
128466
+ frames.length = 0;
128467
+ if (!finished) {
128468
+ ensureStarted();
128469
+ closeActiveBlock();
128470
+ const stopReason = sawToolUse ? "tool_use" : "end_turn";
128471
+ frames.push({
128472
+ event: "message_delta",
128473
+ data: {
128474
+ type: "message_delta",
128475
+ delta: { stop_reason: stopReason, stop_sequence: null },
128476
+ usage
128477
+ }
128478
+ });
128479
+ frames.push({
128480
+ event: "message_stop",
128481
+ data: { type: "message_stop" }
128482
+ });
128483
+ finished = true;
128484
+ }
128485
+ return { frames: [...frames], done: true };
128486
+ };
128487
+ return { pushChunk, finish };
128488
+ }
128489
+
128490
+ // src/antigravity/cloudUpstream.ts
128491
+ var GEMINI_API_BASE_URL = "https://generativelanguage.googleapis.com";
128492
+ function buildCloudUrl(config2, model) {
128493
+ const { cloud } = config2;
128494
+ if (cloud.projectId !== void 0 && cloud.location !== void 0) {
128495
+ const base2 = cloud.endpoint ?? `https://${cloud.location}-aiplatform.googleapis.com`;
128496
+ return `${base2}/v1/projects/${cloud.projectId}/locations/${cloud.location}/publishers/google/models/${encodeURIComponent(model)}:streamGenerateContent?alt=sse`;
128497
+ }
128498
+ const base = cloud.endpoint ?? GEMINI_API_BASE_URL;
128499
+ return `${base}/v1beta/models/${encodeURIComponent(model)}:streamGenerateContent?alt=sse`;
128500
+ }
128501
+ function buildCloudHeaders(token, credentialTarget) {
128502
+ const headers = {
128503
+ "Content-Type": "application/json",
128504
+ Accept: "text/event-stream"
128505
+ };
128506
+ if (credentialTarget === "apiKey") {
128507
+ headers["x-goog-api-key"] = token;
128508
+ } else {
128509
+ headers.Authorization = `Bearer ${token}`;
128510
+ }
128511
+ return headers;
128512
+ }
128513
+ var AntigravityUpstreamError = class extends Error {
128514
+ status;
128515
+ retryAfter;
128516
+ constructor(status, message, retryAfter) {
128517
+ super(`Google Antigravity API error (${String(status)}): ${message}`);
128518
+ this.name = "AntigravityUpstreamError";
128519
+ this.status = status;
128520
+ this.retryAfter = retryAfter;
128521
+ }
128522
+ };
128523
+ async function* callCloudAntigravity(params, fetchFn = fetch) {
128524
+ const url2 = buildCloudUrl(params.config, params.model);
128525
+ const headers = buildCloudHeaders(params.token, params.credentialTarget);
128526
+ const response = await fetchFn(url2, {
128527
+ method: "POST",
128528
+ headers,
128529
+ body: JSON.stringify(params.request),
128530
+ signal: params.signal
128531
+ });
128532
+ if (!response.ok) {
128533
+ const errorText = await response.text();
128534
+ const retryAfter = response.headers.get("retry-after");
128535
+ throw new AntigravityUpstreamError(response.status, errorText, retryAfter);
128536
+ }
128537
+ if (response.body === null) {
128538
+ return;
128539
+ }
128540
+ const decoder = new TextDecoder("utf-8");
128541
+ let buffer2 = "";
128542
+ const sseDataPrefix = "data:";
128543
+ for await (const rawChunk of response.body) {
128544
+ const chunk = rawChunk instanceof Uint8Array ? rawChunk : Buffer.from(String(rawChunk));
128545
+ buffer2 += decoder.decode(chunk, { stream: true });
128546
+ const lines = buffer2.split("\n");
128547
+ buffer2 = lines.pop() ?? "";
128548
+ for (const line of lines) {
128549
+ const trimmed = line.trim();
128550
+ if (trimmed.startsWith(sseDataPrefix)) {
128551
+ const jsonStr = trimmed.slice(sseDataPrefix.length).trim();
128552
+ if (jsonStr.length > 0) {
128553
+ try {
128554
+ const parsed = JSON.parse(jsonStr);
128555
+ if (typeof parsed === "object" && parsed !== null && !Array.isArray(parsed)) {
128556
+ yield parsed;
128557
+ }
128558
+ } catch {
128559
+ }
128560
+ }
128561
+ }
128562
+ }
128563
+ }
128564
+ }
128565
+
128566
+ // src/antigravity/localUpstream.ts
128567
+ var import_node_child_process6 = require("node:child_process");
128568
+ var import_node_net2 = __toESM(require("node:net"), 1);
128569
+ var import_node_readline2 = __toESM(require("node:readline"), 1);
128570
+ init_zod();
128571
+ var DEFAULT_ACP_COMMAND = ["antigravity-acp"];
128572
+ function connectSocket(socketPath) {
128573
+ const socket = import_node_net2.default.createConnection({ path: socketPath });
128574
+ const rl2 = import_node_readline2.default.createInterface({ input: socket, crlfDelay: Infinity });
128575
+ return {
128576
+ send: (msg) => {
128577
+ socket.write(`${JSON.stringify(msg)}
128578
+ `);
128579
+ },
128580
+ lines: rl2,
128581
+ close: () => {
128582
+ socket.destroy();
128583
+ }
128584
+ };
128585
+ }
128586
+ function spawnProcess(command, signal) {
128587
+ const bin = command[0];
128588
+ if (bin === void 0) {
128589
+ throw new Error("ACP command cannot be empty");
128590
+ }
128591
+ const args = command.slice(1);
128592
+ const proc = (0, import_node_child_process6.spawn)(bin, args, {
128593
+ stdio: ["pipe", "pipe", "inherit"],
128594
+ signal
128595
+ });
128596
+ if (proc.stdin === null || proc.stdout === null) {
128597
+ throw new Error(`Failed to establish stdio pipes with ACP process "${command.join(" ")}"`);
128598
+ }
128599
+ const rl2 = import_node_readline2.default.createInterface({ input: proc.stdout, crlfDelay: Infinity });
128600
+ return {
128601
+ send: (msg) => {
128602
+ proc.stdin?.write(`${JSON.stringify(msg)}
128603
+ `);
128604
+ },
128605
+ lines: rl2,
128606
+ close: () => {
128607
+ try {
128608
+ proc.kill("SIGTERM");
128609
+ } catch {
128610
+ }
128611
+ }
128612
+ };
128613
+ }
128614
+ var AcpStreamMessageSchema = external_exports.looseObject({
128615
+ jsonrpc: external_exports.string().optional(),
128616
+ id: external_exports.union([external_exports.number(), external_exports.string()]).optional(),
128617
+ method: external_exports.string().optional(),
128618
+ params: external_exports.looseObject({
128619
+ delta: external_exports.looseObject({
128620
+ text: external_exports.string().optional(),
128621
+ toolCall: external_exports.looseObject({
128622
+ id: external_exports.string().optional(),
128623
+ name: external_exports.string(),
128624
+ arguments: external_exports.string().optional()
128625
+ }).optional()
128626
+ }).optional(),
128627
+ finishReason: external_exports.string().optional(),
128628
+ chunk: external_exports.looseObject({}).optional()
128629
+ }).optional(),
128630
+ result: external_exports.looseObject({
128631
+ chunk: external_exports.looseObject({}).optional()
128632
+ }).optional()
128633
+ });
128634
+ function isRecord7(value2) {
128635
+ return typeof value2 === "object" && value2 !== null && !Array.isArray(value2);
128636
+ }
128637
+ function normalizeFinishReason(reason) {
128638
+ if (reason === void 0) {
128639
+ return void 0;
128640
+ }
128641
+ if (reason === "STOP" || reason === "MAX_TOKENS" || reason === "SAFETY" || reason === "RECITATION" || reason === "OTHER") {
128642
+ return reason;
128643
+ }
128644
+ const lower = reason.toLowerCase();
128645
+ if (lower === "stop" || lower === "end_turn") {
128646
+ return "STOP";
128647
+ }
128648
+ if (lower === "max_tokens" || lower === "length") {
128649
+ return "MAX_TOKENS";
128650
+ }
128651
+ return "OTHER";
128652
+ }
128653
+ function parseJsonRecord(raw) {
128654
+ if (raw === void 0) {
128655
+ return {};
128656
+ }
128657
+ try {
128658
+ const parsed = JSON.parse(raw);
128659
+ if (isRecord7(parsed)) {
128660
+ return parsed;
128661
+ }
128662
+ } catch {
128663
+ }
128664
+ return {};
128665
+ }
128666
+ async function* callLocalAntigravity(params) {
128667
+ const { config: config2, signal } = params;
128668
+ let conn;
128669
+ try {
128670
+ if (params.connector !== void 0) {
128671
+ conn = params.connector(config2, signal);
128672
+ } else if (config2.local.socketPath !== void 0) {
128673
+ conn = connectSocket(config2.local.socketPath);
128674
+ } else {
128675
+ const cmd = config2.local.command ?? DEFAULT_ACP_COMMAND;
128676
+ conn = spawnProcess(cmd, signal);
128677
+ }
128678
+ let nextId = 1;
128679
+ const initId = nextId++;
128680
+ conn.send({
128681
+ jsonrpc: "2.0",
128682
+ id: initId,
128683
+ method: "initialize",
128684
+ params: {
128685
+ protocolVersion: "1.0",
128686
+ clientInfo: { name: "agent-shim", version: "1.0" }
128687
+ }
128688
+ });
128689
+ const promptId = nextId++;
128690
+ conn.send({
128691
+ jsonrpc: "2.0",
128692
+ id: promptId,
128693
+ method: "session/prompt",
128694
+ params: {
128695
+ model: params.model,
128696
+ request: params.request
128697
+ }
128698
+ });
128699
+ for await (const line of conn.lines) {
128700
+ if (signal.aborted) {
128701
+ break;
128702
+ }
128703
+ const trimmed = line.trim();
128704
+ if (trimmed.length === 0) {
128705
+ continue;
128706
+ }
128707
+ try {
128708
+ const parsedJson = JSON.parse(trimmed);
128709
+ const parsed = AcpStreamMessageSchema.safeParse(parsedJson);
128710
+ if (!parsed.success) {
128711
+ continue;
128712
+ }
128713
+ const msg = parsed.data;
128714
+ if (msg.params?.chunk !== void 0) {
128715
+ yield msg.params.chunk;
128716
+ } else if (msg.result?.chunk !== void 0) {
128717
+ yield msg.result.chunk;
128718
+ } else if (msg.method === "session/update" && msg.params?.delta !== void 0) {
128719
+ const delta = msg.params.delta;
128720
+ const parts = [];
128721
+ if (delta.text !== void 0 && delta.text.length > 0) {
128722
+ parts.push({ text: delta.text });
128723
+ }
128724
+ if (delta.toolCall !== void 0) {
128725
+ const argsObj = parseJsonRecord(delta.toolCall.arguments);
128726
+ parts.push({ functionCall: { name: delta.toolCall.name, args: argsObj } });
128727
+ }
128728
+ yield {
128729
+ candidates: [
128730
+ {
128731
+ content: { parts },
128732
+ finishReason: normalizeFinishReason(msg.params.finishReason)
128733
+ }
128734
+ ]
128735
+ };
128736
+ }
128737
+ } catch {
128738
+ }
128739
+ }
128740
+ } finally {
128741
+ conn?.close();
128742
+ }
128743
+ }
128744
+
128745
+ // src/antigravity/quota.ts
128746
+ var MS_PER_SECOND9 = 1e3;
128747
+ var DEFAULT_RETRY_AFTER_SECONDS = 60;
128748
+ var PERCENT_MULTIPLIER = 100;
128749
+ var EXHAUSTED_PERCENT2 = "100";
128750
+ var GEMINI_5H_KEYS = ["gemini-5h", "gemini_5h", "gemini"];
128751
+ var GEMINI_WEEKLY_KEYS = ["gemini-weekly", "gemini_weekly"];
128752
+ var THIRD_PARTY_5H_KEYS = ["3p-5h", "claude-5h", "3p_5h", "claude_5h", "claude"];
128753
+ var THIRD_PARTY_WEEKLY_KEYS = ["3p-weekly", "claude-weekly", "3p_weekly", "claude_weekly"];
128754
+ function findBucket(quota, keys) {
128755
+ for (const key of keys) {
128756
+ const bucket = quota[key];
128757
+ if (bucket !== void 0) {
128758
+ return bucket;
128759
+ }
128760
+ }
128761
+ return void 0;
128762
+ }
128763
+ function calculateUtilization(remainingFraction) {
128764
+ if (remainingFraction === void 0 || !Number.isFinite(remainingFraction)) {
128765
+ return void 0;
128766
+ }
128767
+ const clampedRem = Math.max(0, Math.min(1, remainingFraction));
128768
+ const used = Math.max(0, 1 - clampedRem);
128769
+ return String(Math.round(used * PERCENT_MULTIPLIER));
128770
+ }
128771
+ function calculateResetTimestamp(nowSec, resetInSeconds) {
128772
+ if (resetInSeconds === void 0 || !Number.isFinite(resetInSeconds) || resetInSeconds < 0) {
128773
+ return void 0;
128774
+ }
128775
+ return String(nowSec + Math.ceil(resetInSeconds));
128776
+ }
128777
+ function parseRetryAfterSeconds(raw, defaultSeconds = DEFAULT_RETRY_AFTER_SECONDS) {
128778
+ if (raw === null || raw === void 0 || raw.trim() === "") {
128779
+ return defaultSeconds;
128780
+ }
128781
+ const numeric = Number(raw);
128782
+ if (Number.isFinite(numeric) && numeric > 0) {
128783
+ return Math.ceil(numeric);
128784
+ }
128785
+ const parsedDate = Date.parse(raw);
128786
+ if (!Number.isNaN(parsedDate)) {
128787
+ const diffSec = Math.ceil((parsedDate - Date.now()) / MS_PER_SECOND9);
128788
+ return Math.max(1, diffSec);
128789
+ }
128790
+ return defaultSeconds;
128791
+ }
128792
+ function unifiedAntigravityQuotaHeaders(params) {
128793
+ const rejected = params.rejected === true;
128794
+ const nowSec = Math.floor(params.nowMs / MS_PER_SECOND9);
128795
+ const headers = {
128796
+ "anthropic-ratelimit-unified-status": rejected ? "rejected" : "allowed"
128797
+ };
128798
+ const modelLower = (params.model ?? "").toLowerCase();
128799
+ const isGemini = modelLower.includes("gemini");
128800
+ const fiveHourKeys = isGemini ? GEMINI_5H_KEYS : THIRD_PARTY_5H_KEYS;
128801
+ const weeklyKeys = isGemini ? GEMINI_WEEKLY_KEYS : THIRD_PARTY_WEEKLY_KEYS;
128802
+ const quota = params.quota ?? {};
128803
+ const b5h = findBucket(quota, fiveHourKeys);
128804
+ const bWk = findBucket(quota, weeklyKeys);
128805
+ const used5h = calculateUtilization(b5h?.remaining_fraction);
128806
+ const reset5h = calculateResetTimestamp(nowSec, b5h?.reset_in_seconds);
128807
+ const used7d = calculateUtilization(bWk?.remaining_fraction);
128808
+ const reset7d = calculateResetTimestamp(nowSec, bWk?.reset_in_seconds);
128809
+ let earliestResetSec;
128810
+ if (used5h !== void 0 && reset5h !== void 0) {
128811
+ headers["anthropic-ratelimit-unified-5h-utilization"] = used5h;
128812
+ headers["anthropic-ratelimit-unified-5h-reset"] = reset5h;
128813
+ earliestResetSec = Number(reset5h);
128814
+ }
128815
+ if (used7d !== void 0 && reset7d !== void 0) {
128816
+ headers["anthropic-ratelimit-unified-7d-utilization"] = used7d;
128817
+ headers["anthropic-ratelimit-unified-7d-reset"] = reset7d;
128818
+ const reset7dSec = Number(reset7d);
128819
+ earliestResetSec = earliestResetSec === void 0 ? reset7dSec : Math.min(earliestResetSec, reset7dSec);
128820
+ }
128821
+ if (rejected) {
128822
+ const retrySec = params.retryAfterSeconds ?? DEFAULT_RETRY_AFTER_SECONDS;
128823
+ const fallbackReset = String(nowSec + retrySec);
128824
+ if (headers["anthropic-ratelimit-unified-5h-utilization"] === void 0) {
128825
+ headers["anthropic-ratelimit-unified-5h-utilization"] = EXHAUSTED_PERCENT2;
128826
+ headers["anthropic-ratelimit-unified-5h-reset"] = fallbackReset;
128827
+ }
128828
+ if (headers["anthropic-ratelimit-unified-7d-utilization"] === void 0) {
128829
+ headers["anthropic-ratelimit-unified-7d-utilization"] = EXHAUSTED_PERCENT2;
128830
+ headers["anthropic-ratelimit-unified-7d-reset"] = fallbackReset;
128831
+ }
128832
+ earliestResetSec = earliestResetSec === void 0 ? nowSec + retrySec : Math.min(earliestResetSec, nowSec + retrySec);
128833
+ }
128834
+ if (earliestResetSec !== void 0) {
128835
+ headers["anthropic-ratelimit-unified-reset"] = String(earliestResetSec);
128836
+ }
128837
+ return headers;
128838
+ }
128839
+
128840
+ // src/antigravity/route.ts
128841
+ function createAntigravityRoute(ports) {
128842
+ const fallbackId = ports.fallbackId ?? (() => (0, import_node_crypto21.randomUUID)());
128843
+ return async (request7) => {
128844
+ await Promise.resolve();
128845
+ if (request7.method !== "POST") {
128846
+ return {
128847
+ status: HTTP_STATUS.badRequest,
128848
+ headers: { "Content-Type": "application/json" },
128849
+ body: JSON.stringify({ type: "error", error: { type: "invalid_request_error", message: "only POST is supported" } })
128850
+ };
128851
+ }
128852
+ const providerName = parseProviderPath(request7.path)?.provider;
128853
+ if (providerName === void 0) {
128854
+ return {
128855
+ status: HTTP_STATUS.notFound,
128856
+ headers: { "Content-Type": "application/json" },
128857
+ body: JSON.stringify({ type: "error", error: { type: "not_found_error", message: "no provider specified in path" } })
128858
+ };
128859
+ }
128860
+ const lookup = ports.loadProvider(providerName);
128861
+ if (!lookup.ok) {
128862
+ return {
128863
+ status: lookup.status,
128864
+ headers: { "Content-Type": "application/json" },
128865
+ body: JSON.stringify({ type: "error", error: { type: "invalid_request_error", message: lookup.message } })
128866
+ };
128867
+ }
128868
+ let parsedJson;
128869
+ try {
128870
+ parsedJson = JSON.parse(request7.body);
128871
+ } catch {
128872
+ return {
128873
+ status: HTTP_STATUS.badRequest,
128874
+ headers: { "Content-Type": "application/json" },
128875
+ body: JSON.stringify({ type: "error", error: { type: "invalid_request_error", message: "malformed JSON body" } })
128876
+ };
128877
+ }
128878
+ const parsed = MessagesRequestSchema.safeParse(parsedJson);
128879
+ if (!parsed.success) {
128880
+ return {
128881
+ status: HTTP_STATUS.badRequest,
128882
+ headers: { "Content-Type": "application/json" },
128883
+ body: JSON.stringify({
128884
+ type: "error",
128885
+ error: {
128886
+ type: "invalid_request_error",
128887
+ message: parsed.error.issues.map((i10) => `${i10.path.join(".")}: ${i10.message}`).join("; ")
128888
+ }
128889
+ })
128890
+ };
128891
+ }
128892
+ const { config: config2, token, credentialTarget } = lookup;
128893
+ const requestedModel = parsed.data.model ?? config2.defaultModel;
128894
+ const translated = translateRequest2(parsed.data, config2);
128895
+ const relay = createAntigravityRelay({
128896
+ requestedModel,
128897
+ toolNames: translated.toolNames,
128898
+ fallbackId
128899
+ });
128900
+ const nowMs = ports.now?.() ?? Date.now();
128901
+ const upstreamChunks2 = config2.mode === "local" ? callLocalAntigravity({
128902
+ config: config2,
128903
+ model: translated.model,
128904
+ request: translated.request,
128905
+ signal: request7.signal,
128906
+ connector: ports.localConnector
128907
+ }) : callCloudAntigravity(
128908
+ {
128909
+ config: config2,
128910
+ model: translated.model,
128911
+ request: translated.request,
128912
+ token,
128913
+ credentialTarget,
128914
+ signal: request7.signal
128915
+ },
128916
+ ports.fetchFn
128917
+ );
128918
+ const iterator = upstreamChunks2[Symbol.asyncIterator]();
128919
+ let firstResult;
128920
+ try {
128921
+ firstResult = await iterator.next();
128922
+ } catch (error63) {
128923
+ if (error63 instanceof AntigravityUpstreamError) {
128924
+ const is429 = error63.status === HTTP_STATUS.tooManyRequests;
128925
+ const retryAfter = is429 ? parseRetryAfterSeconds(error63.retryAfter) : void 0;
128926
+ const quotaHeaders3 = unifiedAntigravityQuotaHeaders({
128927
+ quota: ports.quotaSource?.(),
128928
+ rejected: is429,
128929
+ nowMs,
128930
+ retryAfterSeconds: retryAfter,
128931
+ model: requestedModel
128932
+ });
128933
+ const errorType = is429 ? "rate_limit_error" : "api_error";
128934
+ return {
128935
+ status: error63.status,
128936
+ headers: {
128937
+ "Content-Type": "application/json",
128938
+ ...quotaHeaders3,
128939
+ ...retryAfter !== void 0 ? { "retry-after": String(retryAfter) } : {}
128940
+ },
128941
+ body: JSON.stringify({ type: "error", error: { type: errorType, message: error63.message } })
128942
+ };
128943
+ }
128944
+ const errMsg = error63 instanceof Error ? error63.message : String(error63);
128945
+ return {
128946
+ status: HTTP_STATUS.badGateway,
128947
+ headers: { "Content-Type": "application/json" },
128948
+ body: JSON.stringify({ type: "error", error: { type: "api_error", message: errMsg } })
128949
+ };
128950
+ }
128951
+ const quotaHeaders2 = unifiedAntigravityQuotaHeaders({
128952
+ quota: ports.quotaSource?.(),
128953
+ rejected: false,
128954
+ nowMs,
128955
+ model: requestedModel
128956
+ });
128957
+ const stream = async function* () {
128958
+ try {
128959
+ if (firstResult.done !== true) {
128960
+ const step2 = relay.pushChunk(firstResult.value);
128961
+ for (const frame of step2.frames) {
128962
+ yield renderSseFrame2(frame);
128963
+ }
128964
+ if (!step2.done) {
128965
+ for (; ; ) {
128966
+ if (request7.signal.aborted) {
128967
+ break;
128968
+ }
128969
+ const nextResult = await iterator.next();
128970
+ if (nextResult.done === true) {
128971
+ break;
128972
+ }
128973
+ const nextStep = relay.pushChunk(nextResult.value);
128974
+ for (const frame of nextStep.frames) {
128975
+ yield renderSseFrame2(frame);
128976
+ }
128977
+ if (nextStep.done) {
128978
+ break;
128979
+ }
128980
+ }
128981
+ }
128982
+ }
128983
+ const finalStep = relay.finish();
128984
+ for (const frame of finalStep.frames) {
128985
+ yield renderSseFrame2(frame);
128986
+ }
128987
+ } catch (error63) {
128988
+ if (!request7.signal.aborted) {
128989
+ const errMsg = error63 instanceof Error ? error63.message : String(error63);
128990
+ yield renderSseFrame2({
128991
+ event: "error",
128992
+ data: { type: "error", error: { type: "api_error", message: errMsg } }
128993
+ });
128994
+ }
128995
+ }
128996
+ };
128997
+ return {
128998
+ status: HTTP_STATUS.ok,
128999
+ headers: {
129000
+ "Content-Type": "text/event-stream",
129001
+ "Cache-Control": "no-cache",
129002
+ Connection: "keep-alive",
129003
+ ...quotaHeaders2
129004
+ },
129005
+ body: stream()
129006
+ };
129007
+ };
129008
+ }
129009
+
129010
+ // src/frontdoor/antigravityMount.ts
129011
+ var ANTIGRAVITY_MAX_BODY_BYTES = 67108864;
129012
+ var BodyTooLargeError2 = class extends Error {
129013
+ constructor() {
129014
+ super("request body too large");
129015
+ this.name = "BodyTooLargeError";
129016
+ }
129017
+ };
129018
+ async function readBody3(request7) {
129019
+ const chunks = [];
129020
+ let size = 0;
129021
+ for await (const chunk of request7.body) {
129022
+ if (!Buffer.isBuffer(chunk)) {
129023
+ throw new TypeError("request body chunk was not a Buffer");
129024
+ }
129025
+ size += chunk.length;
129026
+ if (size > ANTIGRAVITY_MAX_BODY_BYTES) {
129027
+ throw new BodyTooLargeError2();
129028
+ }
129029
+ chunks.push(chunk);
129030
+ }
129031
+ return Buffer.concat(chunks).toString("utf8");
129032
+ }
129033
+ async function writeRouteResponse2(routed, response, signal) {
129034
+ response.start(routed.status, routed.headers);
129035
+ if (typeof routed.body === "string") {
129036
+ await response.write(routed.body);
129037
+ response.end();
129038
+ return;
129039
+ }
129040
+ for await (const chunk of routed.body) {
129041
+ if (signal.aborted) {
129042
+ return;
129043
+ }
129044
+ await response.write(chunk);
129045
+ }
129046
+ response.end();
129047
+ }
129048
+ function createAntigravityRouteMount(ports, upstreamBase, provider) {
129049
+ const route = createAntigravityRoute(ports);
129050
+ return {
129051
+ name: `antigravity:${provider}`,
129052
+ headroomEligible: true,
129053
+ headroomUpstream: upstreamBase,
129054
+ serve: async (request7, response) => {
129055
+ let body;
129056
+ try {
129057
+ body = await readBody3(request7);
129058
+ } catch (error63) {
129059
+ const tooLarge = error63 instanceof BodyTooLargeError2;
129060
+ response.start(tooLarge ? HTTP_STATUS.payloadTooLarge : HTTP_STATUS.badRequest, { "Content-Type": "application/json" });
129061
+ await response.write(
129062
+ JSON.stringify({ type: "error", error: { type: "invalid_request_error", message: error63 instanceof Error ? error63.message : String(error63) } })
129063
+ );
129064
+ response.end();
129065
+ request7.body.resume();
129066
+ return;
129067
+ }
129068
+ const path59 = new URL(request7.url, "http://127.0.0.1").pathname;
129069
+ const translated = { method: request7.method, path: path59, body, signal: request7.signal };
129070
+ const routed = await route(translated);
129071
+ if (request7.signal.aborted) {
129072
+ return;
129073
+ }
129074
+ await writeRouteResponse2(routed, response, request7.signal);
129075
+ }
129076
+ };
129077
+ }
129078
+
128027
129079
  // src/frontdoor/passthrough.ts
128028
129080
  var http5 = __toESM(require("node:http"), 1);
128029
129081
  var https4 = __toESM(require("node:https"), 1);
@@ -128238,6 +129290,36 @@ function createProviderRouteResolver(deps) {
128238
129290
  )
128239
129291
  };
128240
129292
  }
129293
+ if (isAntigravityProvider(definition)) {
129294
+ const antigravityProvider = definition;
129295
+ const config2 = resolveAntigravityConfig(antigravityProvider.antigravity);
129296
+ return {
129297
+ ok: true,
129298
+ route: createAntigravityRouteMount(
129299
+ {
129300
+ loadProvider: () => {
129301
+ const res = resolveCredential({
129302
+ credential: antigravityProvider.credential,
129303
+ env: deps.env,
129304
+ port: deps.credentials,
129305
+ subject: `provider ${provider}`
129306
+ });
129307
+ if (!res.ok) {
129308
+ return { ok: false, status: HTTP_STATUS.unauthorized, message: res.message };
129309
+ }
129310
+ return {
129311
+ ok: true,
129312
+ config: config2,
129313
+ token: res.credential.token,
129314
+ credentialTarget: antigravityProvider.credential.target
129315
+ };
129316
+ }
129317
+ },
129318
+ directOrigin2(deps.directPort()),
129319
+ provider
129320
+ )
129321
+ };
129322
+ }
128241
129323
  const httpProvider = definition;
128242
129324
  return {
128243
129325
  ok: true,
@@ -128277,7 +129359,7 @@ function createProviderRouteResolver(deps) {
128277
129359
  let routes;
128278
129360
  try {
128279
129361
  const definition = providerName === void 0 ? void 0 : loadProvider(deps.providersDir, providerName, deps.fs);
128280
- routes = definition === void 0 || isCodexProvider(definition) ? void 0 : definition.routes;
129362
+ routes = definition === void 0 || !isHttpProvider(definition) ? void 0 : definition.routes;
128281
129363
  } catch {
128282
129364
  routes = void 0;
128283
129365
  }
@@ -128357,7 +129439,7 @@ function attachingProviderCredential(route, deps) {
128357
129439
  init_realFrontDoorPort();
128358
129440
 
128359
129441
  // src/frontdoor/rcCommands.ts
128360
- var import_node_crypto20 = require("node:crypto");
129442
+ var import_node_crypto22 = require("node:crypto");
128361
129443
  init_commandDeps();
128362
129444
  init_cliError();
128363
129445
  init_realPorts();
@@ -128396,15 +129478,15 @@ function readFrontDoorControlMaterial(fsPort, paths, purpose) {
128396
129478
 
128397
129479
  // src/frontdoor/rcLiveUsage.ts
128398
129480
  var RC_RATE_LIMIT_EVENT_TYPE = "rate_limit_event";
128399
- function isRecord6(value2) {
129481
+ function isRecord8(value2) {
128400
129482
  return typeof value2 === "object" && value2 !== null && !Array.isArray(value2);
128401
129483
  }
128402
129484
  function rcRateLimitInfoOf(event) {
128403
129485
  const payload = event.envelope.payload;
128404
- if (!isRecord6(payload) || payload.type !== RC_RATE_LIMIT_EVENT_TYPE) {
129486
+ if (!isRecord8(payload) || payload.type !== RC_RATE_LIMIT_EVENT_TYPE) {
128405
129487
  return void 0;
128406
129488
  }
128407
- if (!isRecord6(payload.rate_limit_info)) {
129489
+ if (!isRecord8(payload.rate_limit_info)) {
128408
129490
  return void 0;
128409
129491
  }
128410
129492
  const parsed = RcRateLimitInfoSchema.safeParse(payload.rate_limit_info);
@@ -128438,9 +129520,9 @@ init_account();
128438
129520
  var RC_SELF_HOST_OAUTH_HOST = "platform.claude.com";
128439
129521
  var RC_SELF_HOST_SCOPE_LIST = ["user:profile", "user:inference", "user:sessions:claude_code", "user:mcp_servers", "user:file_upload"];
128440
129522
  var RC_SELF_HOST_OAUTH_TOKEN_TTL_SECONDS = 3600;
128441
- var MS_PER_SECOND9 = 1e3;
129523
+ var MS_PER_SECOND10 = 1e3;
128442
129524
  var HTTP_SERVICE_UNAVAILABLE = 503;
128443
- function isRecord7(value2) {
129525
+ function isRecord9(value2) {
128444
129526
  return typeof value2 === "object" && value2 !== null && !Array.isArray(value2);
128445
129527
  }
128446
129528
  function parseJsonObject2(body) {
@@ -128450,7 +129532,7 @@ function parseJsonObject2(body) {
128450
129532
  } catch {
128451
129533
  return void 0;
128452
129534
  }
128453
- return isRecord7(parsed) ? parsed : void 0;
129535
+ return isRecord9(parsed) ? parsed : void 0;
128454
129536
  }
128455
129537
  function growthBookFeatures() {
128456
129538
  return {
@@ -128494,7 +129576,7 @@ function createRcSelfHostLocal(deps) {
128494
129576
  }
128495
129577
  if (method === "POST" && pathname.startsWith("/api/eval/")) {
128496
129578
  await deps.readBody(request7, CONTROL_BODY_CAP_BYTES);
128497
- answerServerJson(response, HTTP_STATUS.ok, { features: growthBookFeatures(), dateUpdated: Math.floor(deps.now() / MS_PER_SECOND9) });
129579
+ answerServerJson(response, HTTP_STATUS.ok, { features: growthBookFeatures(), dateUpdated: Math.floor(deps.now() / MS_PER_SECOND10) });
128498
129580
  return true;
128499
129581
  }
128500
129582
  if (method === "GET" && pathname === "/api/oauth/profile") {
@@ -128544,7 +129626,7 @@ var RC_SELF_HOST_RECORD_DIR = "rc-selfhost";
128544
129626
  var RC_SELF_HOST_RECORD_FILE = "credential.json";
128545
129627
  var SELF_HOST_EMAIL = "selfhost@agent-shim.invalid";
128546
129628
  var SELF_HOST_SUBSCRIPTION_TYPE = "max";
128547
- function isRecord8(value2) {
129629
+ function isRecord10(value2) {
128548
129630
  return typeof value2 === "object" && value2 !== null && !Array.isArray(value2);
128549
129631
  }
128550
129632
  function readJsonObject(fs24, file2) {
@@ -128558,7 +129640,7 @@ function readJsonObject(fs24, file2) {
128558
129640
  } catch {
128559
129641
  return void 0;
128560
129642
  }
128561
- return isRecord8(parsed) ? parsed : void 0;
129643
+ return isRecord10(parsed) ? parsed : void 0;
128562
129644
  }
128563
129645
  function readRcSelfHostRecord(fs24, frontdoorDir) {
128564
129646
  const parsed = readJsonObject(fs24, import_node_path49.default.join(frontdoorDir, RC_SELF_HOST_RECORD_DIR, RC_SELF_HOST_RECORD_FILE));
@@ -128582,7 +129664,7 @@ function mintRcSelfHostCredential(deps) {
128582
129664
  const recordFile = import_node_path49.default.join(recordDir, RC_SELF_HOST_RECORD_FILE);
128583
129665
  const previousRecord = readRcSelfHostRecord(deps.fs, deps.frontdoorDir);
128584
129666
  const existingCredentials = readJsonObject(deps.fs, credentialsFile);
128585
- const existingOauth = isRecord8(existingCredentials?.claudeAiOauth) ? existingCredentials.claudeAiOauth : void 0;
129667
+ const existingOauth = isRecord10(existingCredentials?.claudeAiOauth) ? existingCredentials.claudeAiOauth : void 0;
128586
129668
  const existingToken = typeof existingOauth?.accessToken === "string" && existingOauth.accessToken !== "" ? existingOauth.accessToken : void 0;
128587
129669
  const existingIsOwn = existingToken !== void 0 && previousRecord?.accessToken === existingToken;
128588
129670
  if (existingToken !== void 0 && !existingIsOwn && !deps.force) {
@@ -128599,7 +129681,7 @@ function mintRcSelfHostCredential(deps) {
128599
129681
  deps.fs.writeFilePrivate(credentialsFile, `${JSON.stringify({ ...existingCredentials, claudeAiOauth: { accessToken, refreshToken, expiresAt: null, scopes: [...RC_SELF_HOST_SCOPE_LIST], subscriptionType: SELF_HOST_SUBSCRIPTION_TYPE, rateLimitTier: null } }, null, 2)}
128600
129682
  `);
128601
129683
  const claudeJson = readJsonObject(deps.fs, claudeJsonFile) ?? {};
128602
- const existingBlock = (value2) => isRecord8(value2) ? value2 : {};
129684
+ const existingBlock = (value2) => isRecord10(value2) ? value2 : {};
128603
129685
  deps.fs.writeFilePrivate(claudeJsonFile, `${JSON.stringify({
128604
129686
  ...claudeJson,
128605
129687
  oauthAccount: {
@@ -128678,12 +129760,12 @@ function eventExcerpt(text2) {
128678
129760
  return text2.length <= RC_PENDING_SUMMARY_EXCERPT_CHARS ? text2 : `${text2.slice(0, RC_PENDING_SUMMARY_EXCERPT_CHARS)}...`;
128679
129761
  }
128680
129762
  var PERCENT_SCALE = 100;
128681
- var MS_PER_SECOND10 = 1e3;
129763
+ var MS_PER_SECOND11 = 1e3;
128682
129764
  function percentOf(fraction) {
128683
129765
  return `${String(Math.round(fraction * PERCENT_SCALE))}%`;
128684
129766
  }
128685
129767
  function resetInstantOf(epochSeconds) {
128686
- return new Date(epochSeconds * MS_PER_SECOND10).toISOString();
129768
+ return new Date(epochSeconds * MS_PER_SECOND11).toISOString();
128687
129769
  }
128688
129770
  function formatRcRateLimitInfo(info) {
128689
129771
  const parts = [info.status];
@@ -128964,8 +130046,8 @@ function registerRcCommand(frontdoor, paths) {
128964
130046
  identitiesDir: paths.identitiesDir,
128965
130047
  frontdoorDir: paths.frontdoorDir,
128966
130048
  identity,
128967
- newUuid: import_node_crypto20.randomUUID,
128968
- randomToken: () => (0, import_node_crypto20.randomBytes)(MINTED_TOKEN_RANDOM_BYTES).toString("base64url"),
130049
+ newUuid: import_node_crypto22.randomUUID,
130050
+ randomToken: () => (0, import_node_crypto22.randomBytes)(MINTED_TOKEN_RANDOM_BYTES).toString("base64url"),
128969
130051
  force: options.force === true,
128970
130052
  now: () => Date.now()
128971
130053
  });
@@ -128986,11 +130068,11 @@ var import_node_path50 = __toESM(require("node:path"), 1);
128986
130068
  function isSafeSessionId(sessionId) {
128987
130069
  return /^[A-Za-z0-9_-]+$/.test(sessionId);
128988
130070
  }
128989
- function isRecord9(value2) {
130071
+ function isRecord11(value2) {
128990
130072
  return typeof value2 === "object" && value2 !== null && !Array.isArray(value2);
128991
130073
  }
128992
130074
  function credentialOfJson(parsed) {
128993
- if (!isRecord9(parsed)) {
130075
+ if (!isRecord11(parsed)) {
128994
130076
  return void 0;
128995
130077
  }
128996
130078
  const { authorization, anthropicVersion, anthropicClientPlatform } = parsed;
@@ -129020,7 +130102,7 @@ function createRcCredentialStore(fs24, dir) {
129020
130102
  } catch {
129021
130103
  return void 0;
129022
130104
  }
129023
- return isRecord9(parsed) ? parsed : void 0;
130105
+ return isRecord11(parsed) ? parsed : void 0;
129024
130106
  };
129025
130107
  return {
129026
130108
  read: (sessionId) => {
@@ -129588,7 +130670,7 @@ init_capability();
129588
130670
  // src/frontdoor/rcSelfHostEndpoints.ts
129589
130671
  var RC_SOURCE_WORKER = "worker";
129590
130672
  var RC_SOURCE_CLIENT = "client";
129591
- function isRecord10(value2) {
130673
+ function isRecord12(value2) {
129592
130674
  return typeof value2 === "object" && value2 !== null && !Array.isArray(value2);
129593
130675
  }
129594
130676
  function parseJsonObject3(body) {
@@ -129598,7 +130680,7 @@ function parseJsonObject3(body) {
129598
130680
  } catch {
129599
130681
  return void 0;
129600
130682
  }
129601
- return isRecord10(parsed) ? parsed : void 0;
130683
+ return isRecord12(parsed) ? parsed : void 0;
129602
130684
  }
129603
130685
  function nonEmptyString2(record2, field) {
129604
130686
  const value2 = record2 === void 0 ? void 0 : record2[field];
@@ -129672,7 +130754,7 @@ async function serveRcClientChannels(ctx, tail, method, maxBatchEvents) {
129672
130754
  }
129673
130755
  const results = [];
129674
130756
  for (const event of events) {
129675
- if (!isRecord10(event) || !isRecord10(event.payload)) {
130757
+ if (!isRecord12(event) || !isRecord12(event.payload)) {
129676
130758
  await ctx.answerJson(response, HTTP_STATUS.badRequest, { type: "error", error: { type: "invalid_request_error", message: "every event in a teleport write is an object carrying one payload object" } });
129677
130759
  return true;
129678
130760
  }
@@ -129772,7 +130854,7 @@ async function serveRcCompatSessions(ctx, pathname, compatPath) {
129772
130854
  // src/frontdoor/rcSelfHostConversations.ts
129773
130855
  var RC_CONVERSATIONS_PATH_PREFIX = "/v1/code/conversations";
129774
130856
  var RC_CONVERSATION_ID_PREFIX = "conv_";
129775
- function isRecord11(value2) {
130857
+ function isRecord13(value2) {
129776
130858
  return typeof value2 === "object" && value2 !== null && !Array.isArray(value2);
129777
130859
  }
129778
130860
  function parseJsonObject4(body) {
@@ -129782,7 +130864,7 @@ function parseJsonObject4(body) {
129782
130864
  } catch {
129783
130865
  return void 0;
129784
130866
  }
129785
- return isRecord11(parsed) ? parsed : void 0;
130867
+ return isRecord13(parsed) ? parsed : void 0;
129786
130868
  }
129787
130869
  function nonEmptyString3(record2, field) {
129788
130870
  const value2 = record2 === void 0 ? void 0 : record2[field];
@@ -129836,7 +130918,7 @@ async function serveRcConversations(ctx, pathname, method) {
129836
130918
  }
129837
130919
  const results = [];
129838
130920
  for (const event of events) {
129839
- if (!isRecord11(event) || !isRecord11(event.payload)) {
130921
+ if (!isRecord13(event) || !isRecord13(event.payload)) {
129840
130922
  await ctx.answerJson(response, HTTP_STATUS.badRequest, { type: "error", error: { type: "invalid_request_error", message: "every event in a write is an object carrying one payload object" } });
129841
130923
  return;
129842
130924
  }
@@ -129866,7 +130948,7 @@ async function serveRcConversations(ctx, pathname, method) {
129866
130948
  var dns2 = __toESM(require("node:dns"), 1);
129867
130949
  var http6 = __toESM(require("node:http"), 1);
129868
130950
  var https5 = __toESM(require("node:https"), 1);
129869
- var net3 = __toESM(require("node:net"), 1);
130951
+ var net4 = __toESM(require("node:net"), 1);
129870
130952
  var RC_WEB_FETCH_MAX_BYTES = 12582912;
129871
130953
  var RC_WEB_FETCH_DEADLINE_MS = 4e4;
129872
130954
  var RC_WEB_FETCH_MAX_REDIRECTS = 20;
@@ -129907,7 +130989,7 @@ function refused(errorType, errorMessage2) {
129907
130989
  return { kind: "refused", errorType: `${ERROR_PREFIX}${errorType}`, errorMessage: errorMessage2 };
129908
130990
  }
129909
130991
  function isPrivateAddress(address) {
129910
- const version2 = net3.isIP(address);
130992
+ const version2 = net4.isIP(address);
129911
130993
  if (version2 === IP_VERSION_4) {
129912
130994
  const octets = address.split(".").map((part) => Number(part));
129913
130995
  const first = octets[0] ?? -1;
@@ -129993,7 +131075,7 @@ async function checkTarget(url2, deps) {
129993
131075
  const hostname3 = url2.hostname.replace(/^\[|\]$/g, "");
129994
131076
  let addresses;
129995
131077
  try {
129996
- addresses = net3.isIP(hostname3) === 0 ? await deps.lookup(hostname3) : [hostname3];
131078
+ addresses = net4.isIP(hostname3) === 0 ? await deps.lookup(hostname3) : [hostname3];
129997
131079
  } catch {
129998
131080
  return refused("resolve", `${hostname3} did not resolve`);
129999
131081
  }
@@ -130118,7 +131200,7 @@ var RC_COMPAT_SESSIONS_PATH = "/v1/sessions";
130118
131200
  var RC_SESSION_ID_PREFIX2 = "cse_";
130119
131201
  var RC_SELF_HOST_API_BASE_URL = "https://api.anthropic.com";
130120
131202
  var HTTP_CONFLICT = 409;
130121
- var MS_PER_SECOND11 = 1e3;
131203
+ var MS_PER_SECOND12 = 1e3;
130122
131204
  var HTTP_SERVICE_UNAVAILABLE2 = 503;
130123
131205
  var RC_SELF_HOST_WORKER_JWT_TTL_SECONDS = 46800;
130124
131206
  var RC_SELF_HOST_KEEPALIVE_MS = 15e3;
@@ -130129,7 +131211,7 @@ var RC_SELF_HOST_WORKER_EPOCH = 1;
130129
131211
  var RC_STREAM_EVENT_NAME = "client_event";
130130
131212
  var CONFLICT_REASON_HEADER2 = "x-ccr-conflict-reason";
130131
131213
  var CONFLICT_REASON_EPOCH_STALE = "epoch_stale";
130132
- function isRecord12(value2) {
131214
+ function isRecord14(value2) {
130133
131215
  return typeof value2 === "object" && value2 !== null && !Array.isArray(value2);
130134
131216
  }
130135
131217
  function isWebSearchRefusal(value2) {
@@ -130185,7 +131267,7 @@ function presentationRefusal(headers) {
130185
131267
  const bearer = presented.slice("bearer ".length);
130186
131268
  return bearer.slice(0, "bearer ".length).toLowerCase() === "bearer " ? "doubled-scheme-word" : "unrecognised";
130187
131269
  }
130188
- async function readBody3(request7, capBytes) {
131270
+ async function readBody4(request7, capBytes) {
130189
131271
  return await new Promise((resolve2, reject) => {
130190
131272
  const chunks = [];
130191
131273
  let total = 0;
@@ -130213,12 +131295,12 @@ function parseJsonObject5(body) {
130213
131295
  } catch {
130214
131296
  return void 0;
130215
131297
  }
130216
- return isRecord12(parsed) ? parsed : void 0;
131298
+ return isRecord14(parsed) ? parsed : void 0;
130217
131299
  }
130218
131300
  function mintWorkerJwt(randomToken, issuedAt) {
130219
131301
  const encode3 = (value2) => Buffer.from(JSON.stringify(value2), "utf8").toString("base64url");
130220
131302
  const header = encode3({ alg: "HS256", typ: "JWT" });
130221
- const payload = encode3({ exp: Math.floor((issuedAt + RC_SELF_HOST_WORKER_JWT_TTL_SECONDS * MS_PER_SECOND11) / MS_PER_SECOND11), iat: Math.floor(issuedAt / MS_PER_SECOND11) });
131303
+ const payload = encode3({ exp: Math.floor((issuedAt + RC_SELF_HOST_WORKER_JWT_TTL_SECONDS * MS_PER_SECOND12) / MS_PER_SECOND12), iat: Math.floor(issuedAt / MS_PER_SECOND12) });
130222
131304
  return `${header}.${payload}.${Buffer.from(randomToken(), "utf8").toString("base64url")}`;
130223
131305
  }
130224
131306
  function createRcSelfHostSurface(deps) {
@@ -130408,7 +131490,7 @@ data: ${JSON.stringify(envelope)}
130408
131490
  await unauthorized(response, refusal2);
130409
131491
  return;
130410
131492
  }
130411
- const body = parseJsonObject5(await readBody3(request7.body, CONTROL_BODY_CAP_BYTES));
131493
+ const body = parseJsonObject5(await readBody4(request7.body, CONTROL_BODY_CAP_BYTES));
130412
131494
  const title = nonEmptyString4(body, "title");
130413
131495
  if (title === void 0) {
130414
131496
  await answerJson2(response, HTTP_STATUS.badRequest, { type: "error", error: { type: "invalid_request_error", message: "a session update is JSON naming a non-empty title" } });
@@ -130463,7 +131545,7 @@ data: ${JSON.stringify(envelope)}
130463
131545
  return;
130464
131546
  }
130465
131547
  if (workerTail === "" && method === "PUT") {
130466
- const body = parseJsonObject5(await readBody3(request7.body, CONTROL_BODY_CAP_BYTES));
131548
+ const body = parseJsonObject5(await readBody4(request7.body, CONTROL_BODY_CAP_BYTES));
130467
131549
  const claimedEpoch = numberOf2(body, "worker_epoch");
130468
131550
  if (claimedEpoch !== void 0 && claimedEpoch !== RC_SELF_HOST_WORKER_EPOCH) {
130469
131551
  await epochStale(response);
@@ -130473,24 +131555,24 @@ data: ${JSON.stringify(envelope)}
130473
131555
  if (status !== void 0) {
130474
131556
  session.workerStatus = status;
130475
131557
  }
130476
- if (isRecord12(body?.external_metadata)) {
131558
+ if (isRecord14(body?.external_metadata)) {
130477
131559
  session.externalMetadata = body.external_metadata;
130478
131560
  }
130479
131561
  await answerJson2(response, HTTP_STATUS.ok, {});
130480
131562
  return;
130481
131563
  }
130482
131564
  if (workerTail === "register" && method === "POST") {
130483
- await readBody3(request7.body, CONTROL_BODY_CAP_BYTES);
131565
+ await readBody4(request7.body, CONTROL_BODY_CAP_BYTES);
130484
131566
  await answerJson2(response, HTTP_STATUS.ok, { worker_epoch: RC_SELF_HOST_WORKER_EPOCH });
130485
131567
  return;
130486
131568
  }
130487
131569
  if (workerTail === "heartbeat" && method === "POST") {
130488
- await readBody3(request7.body, CONTROL_BODY_CAP_BYTES);
131570
+ await readBody4(request7.body, CONTROL_BODY_CAP_BYTES);
130489
131571
  await answerJson2(response, HTTP_STATUS.ok, {});
130490
131572
  return;
130491
131573
  }
130492
131574
  if (workerTail === "events" && method === "POST") {
130493
- const body = parseJsonObject5(await readBody3(request7.body, CONTROL_BODY_CAP_BYTES));
131575
+ const body = parseJsonObject5(await readBody4(request7.body, CONTROL_BODY_CAP_BYTES));
130494
131576
  const claimedEpoch = numberOf2(body, "worker_epoch");
130495
131577
  if (claimedEpoch !== void 0 && claimedEpoch !== RC_SELF_HOST_WORKER_EPOCH) {
130496
131578
  await epochStale(response);
@@ -130503,7 +131585,7 @@ data: ${JSON.stringify(envelope)}
130503
131585
  }
130504
131586
  const results = [];
130505
131587
  for (const event of events) {
130506
- if (!isRecord12(event) || !isRecord12(event.payload)) {
131588
+ if (!isRecord14(event) || !isRecord14(event.payload)) {
130507
131589
  await answerJson2(response, HTTP_STATUS.badRequest, { type: "error", error: { type: "invalid_request_error", message: "every event in a batch is an object carrying one payload object" } });
130508
131590
  return;
130509
131591
  }
@@ -130519,12 +131601,12 @@ data: ${JSON.stringify(envelope)}
130519
131601
  return;
130520
131602
  }
130521
131603
  if (workerTail === "events/delivery" && method === "POST") {
130522
- await readBody3(request7.body, CONTROL_BODY_CAP_BYTES);
131604
+ await readBody4(request7.body, CONTROL_BODY_CAP_BYTES);
130523
131605
  await answerJson2(response, HTTP_STATUS.ok, {});
130524
131606
  return;
130525
131607
  }
130526
131608
  if (workerTail === "internal-events" && method === "POST") {
130527
- const body = parseJsonObject5(await readBody3(request7.body, CONTROL_BODY_CAP_BYTES));
131609
+ const body = parseJsonObject5(await readBody4(request7.body, CONTROL_BODY_CAP_BYTES));
130528
131610
  const claimedEpoch = numberOf2(body, "worker_epoch");
130529
131611
  if (claimedEpoch !== void 0 && claimedEpoch !== RC_SELF_HOST_WORKER_EPOCH) {
130530
131612
  await epochStale(response);
@@ -130536,7 +131618,7 @@ data: ${JSON.stringify(envelope)}
130536
131618
  return;
130537
131619
  }
130538
131620
  for (const event of events) {
130539
- if (isRecord12(event)) {
131621
+ if (isRecord14(event)) {
130540
131622
  session.internalEvents.push({ eventId: deps.newUuid(), body: event });
130541
131623
  }
130542
131624
  }
@@ -130559,12 +131641,12 @@ data: ${JSON.stringify(envelope)}
130559
131641
  return;
130560
131642
  }
130561
131643
  if (workerTail === "diagnostics" && method === "POST") {
130562
- await readBody3(request7.body, CONTROL_BODY_CAP_BYTES);
131644
+ await readBody4(request7.body, CONTROL_BODY_CAP_BYTES);
130563
131645
  await answerJson2(response, HTTP_STATUS.ok, {});
130564
131646
  return;
130565
131647
  }
130566
131648
  if (workerTail === "web-fetch" && method === "POST") {
130567
- const body = parseJsonObject5(await readBody3(request7.body, CONTROL_BODY_CAP_BYTES));
131649
+ const body = parseJsonObject5(await readBody4(request7.body, CONTROL_BODY_CAP_BYTES));
130568
131650
  const target = nonEmptyString4(body, "url");
130569
131651
  if (target === void 0) {
130570
131652
  await answerJson2(response, HTTP_STATUS.badRequest, { type: "error", error: { type: "invalid_request_error", message: "a worker web-fetch carries one url" } });
@@ -130587,7 +131669,7 @@ data: ${JSON.stringify(envelope)}
130587
131669
  return;
130588
131670
  }
130589
131671
  if (workerTail === "web-search" && method === "POST") {
130590
- const body = parseJsonObject5(await readBody3(request7.body, CONTROL_BODY_CAP_BYTES));
131672
+ const body = parseJsonObject5(await readBody4(request7.body, CONTROL_BODY_CAP_BYTES));
130591
131673
  const query = nonEmptyString4(body, "query");
130592
131674
  if (query === void 0) {
130593
131675
  await answerJson2(response, HTTP_STATUS.badRequest, { type: "error", error: { type: "invalid_request_error", message: "a worker web-search carries one query" } });
@@ -130624,7 +131706,7 @@ data: ${JSON.stringify(envelope)}
130624
131706
  return;
130625
131707
  }
130626
131708
  if (tail === "events" && method === "POST") {
130627
- const body = parseJsonObject5(await readBody3(request7.body, CONTROL_BODY_CAP_BYTES));
131709
+ const body = parseJsonObject5(await readBody4(request7.body, CONTROL_BODY_CAP_BYTES));
130628
131710
  const events = body?.events;
130629
131711
  if (!Array.isArray(events) || events.length === 0 || events.length > RC_SELF_HOST_MAX_BATCH_EVENTS) {
130630
131712
  await answerJson2(response, HTTP_STATUS.badRequest, { type: "error", error: { type: "invalid_request_error", message: `a client event write is a non-empty array of at most ${String(RC_SELF_HOST_MAX_BATCH_EVENTS)} events` } });
@@ -130632,7 +131714,7 @@ data: ${JSON.stringify(envelope)}
130632
131714
  }
130633
131715
  const results = [];
130634
131716
  for (const event of events) {
130635
- if (!isRecord12(event) || !isRecord12(event.payload)) {
131717
+ if (!isRecord14(event) || !isRecord14(event.payload)) {
130636
131718
  await answerJson2(response, HTTP_STATUS.badRequest, { type: "error", error: { type: "invalid_request_error", message: "every event in a write is an object carrying one payload object" } });
130637
131719
  return;
130638
131720
  }
@@ -130651,7 +131733,7 @@ data: ${JSON.stringify(envelope)}
130651
131733
  await holdStream(session.conversation, session.id, "clientStreams", () => true, request7, response);
130652
131734
  return;
130653
131735
  }
130654
- if (await serveRcClientChannels({ request: request7, response, host: { id: session.id, clients: session.clients, conversation: session.conversation, writer: { session: session.id, half: "client" } }, answerJson: answerJson2, readBody: readBody3, publish, sweep, now: deps.now, presenceRefreshSeconds: RC_PRESENCE_REFRESH_SECONDS, ...deps.log === void 0 ? {} : { log: deps.log } }, tail, method, RC_SELF_HOST_MAX_BATCH_EVENTS)) {
131736
+ if (await serveRcClientChannels({ request: request7, response, host: { id: session.id, clients: session.clients, conversation: session.conversation, writer: { session: session.id, half: "client" } }, answerJson: answerJson2, readBody: readBody4, publish, sweep, now: deps.now, presenceRefreshSeconds: RC_PRESENCE_REFRESH_SECONDS, ...deps.log === void 0 ? {} : { log: deps.log } }, tail, method, RC_SELF_HOST_MAX_BATCH_EVENTS)) {
130655
131737
  return;
130656
131738
  }
130657
131739
  await answerJson2(response, HTTP_STATUS.notFound, { type: "error", error: { type: "api_error", message: `the self-hosted Remote Control surface serves no path "${tail}"` } });
@@ -130669,11 +131751,11 @@ data: ${JSON.stringify(envelope)}
130669
131751
  return;
130670
131752
  }
130671
131753
  if (pathname === RC_COMPAT_SESSIONS_PATH || pathname.startsWith(`${RC_COMPAT_SESSIONS_PATH}/`)) {
130672
- await serveRcCompatSessions({ request: request7, response, sessions, retireSession, answerJson: answerJson2, readBody: readBody3, credentialRefusal, unauthorized, now: deps.now, ...deps.log === void 0 ? {} : { log: deps.log } }, pathname, RC_COMPAT_SESSIONS_PATH);
131754
+ await serveRcCompatSessions({ request: request7, response, sessions, retireSession, answerJson: answerJson2, readBody: readBody4, credentialRefusal, unauthorized, now: deps.now, ...deps.log === void 0 ? {} : { log: deps.log } }, pathname, RC_COMPAT_SESSIONS_PATH);
130673
131755
  return;
130674
131756
  }
130675
131757
  if (pathname === RC_CONVERSATIONS_PATH_PREFIX || pathname.startsWith(`${RC_CONVERSATIONS_PATH_PREFIX}/`)) {
130676
- await serveRcConversations({ request: request7, response, conversations, answerJson: answerJson2, readBody: readBody3, credentialRefusal, unauthorized, publish, holdStream, sweep, now: deps.now, presenceRefreshSeconds: RC_PRESENCE_REFRESH_SECONDS, maxBatchEvents: RC_SELF_HOST_MAX_BATCH_EVENTS, ...deps.log === void 0 ? {} : { log: deps.log } }, pathname, method);
131758
+ await serveRcConversations({ request: request7, response, conversations, answerJson: answerJson2, readBody: readBody4, credentialRefusal, unauthorized, publish, holdStream, sweep, now: deps.now, presenceRefreshSeconds: RC_PRESENCE_REFRESH_SECONDS, maxBatchEvents: RC_SELF_HOST_MAX_BATCH_EVENTS, ...deps.log === void 0 ? {} : { log: deps.log } }, pathname, method);
130677
131759
  return;
130678
131760
  }
130679
131761
  if (pathname !== RC_SESSIONS_PATH_PREFIX2 && !pathname.startsWith(`${RC_SESSIONS_PATH_PREFIX2}/`)) {
@@ -130687,7 +131769,7 @@ data: ${JSON.stringify(envelope)}
130687
131769
  await unauthorized(response, createRefusal);
130688
131770
  return;
130689
131771
  }
130690
- const body = parseJsonObject5(await readBody3(request7.body, CONTROL_BODY_CAP_BYTES));
131772
+ const body = parseJsonObject5(await readBody4(request7.body, CONTROL_BODY_CAP_BYTES));
130691
131773
  const namedConversation = nonEmptyString4(body, "conversation");
130692
131774
  let conversation;
130693
131775
  if (namedConversation === void 0) {
@@ -130742,7 +131824,7 @@ data: ${JSON.stringify(envelope)}
130742
131824
  await serveSessionPath(sessions.get(id2), tail, request7, response);
130743
131825
  }
130744
131826
  };
130745
- const local = createRcSelfHostLocal({ now: deps.now, credentialRecord: deps.credentialRecord, readBody: readBody3 });
131827
+ const local = createRcSelfHostLocal({ now: deps.now, credentialRecord: deps.credentialRecord, readBody: readBody4 });
130746
131828
  return {
130747
131829
  route,
130748
131830
  local,
@@ -130822,7 +131904,7 @@ function createSseParser() {
130822
131904
  }
130823
131905
  };
130824
131906
  }
130825
- function isRecord13(value2) {
131907
+ function isRecord15(value2) {
130826
131908
  return typeof value2 === "object" && value2 !== null && !Array.isArray(value2);
130827
131909
  }
130828
131910
  function sequenceNumOf(value2) {
@@ -130844,7 +131926,7 @@ function parseRcStreamEnvelope(parsed) {
130844
131926
  } catch {
130845
131927
  return void 0;
130846
131928
  }
130847
- if (!isRecord13(data)) {
131929
+ if (!isRecord15(data)) {
130848
131930
  return void 0;
130849
131931
  }
130850
131932
  const eventType = data.event_type;
@@ -131081,15 +132163,20 @@ function createRcStreamHub(deps) {
131081
132163
 
131082
132164
  // src/frontdoor/watchdog.ts
131083
132165
  var import_node_worker_threads2 = require("node:worker_threads");
132166
+ init_schema();
131084
132167
  init_ensure2();
131085
132168
  init_probe();
131086
132169
  var DOOR_STALL_BOUND_MS = 2 * FRONTDOOR_PROBE_ATTEMPTS * PROBE_TIMEOUT_MS;
132170
+ var MS_PER_MINUTE4 = 6e4;
132171
+ var DOOR_RESPAWN_MIN_SERVING_MS = FRONTDOOR_DEFAULT_IDLE_SHUTDOWN_MINUTES * MS_PER_MINUTE4;
132172
+ var DOOR_AWAIT_PID_ENV = "AGENT_SHIM_FRONTDOOR_AWAIT_PID";
131087
132173
  var CHECKS_PER_PROBE_DEADLINE = 2;
131088
132174
  var DOOR_WATCHDOG_CHECK_MS = PROBE_TIMEOUT_MS / CHECKS_PER_PROBE_DEADLINE;
131089
132175
  var WATCHDOG_SOURCE = `
131090
132176
  const { workerData, parentPort } = require("node:worker_threads");
131091
132177
  const fs = require("node:fs");
131092
- const { shared, boundMs, checkEveryMs, stateFile, ownPid, action } = workerData;
132178
+ const { shared, boundMs, checkEveryMs, stateFile, ownPid, action, logFile, respawn, respawnAfterServingMs, awaitPidEnv } = workerData;
132179
+ const startedAt = Date.now();
131093
132180
  const counter = new Int32Array(shared);
131094
132181
  let lastValue = Atomics.load(counter, 0);
131095
132182
  let lastChangeAt = Date.now();
@@ -131106,6 +132193,31 @@ const record = (message) => {
131106
132193
  // The state file is a courtesy to whoever looks next; the process still has to end.
131107
132194
  }
131108
132195
  };
132196
+ const log = (line) => {
132197
+ if (logFile === undefined) return;
132198
+ try {
132199
+ fs.appendFileSync(logFile, new Date().toISOString() + " frontdoor " + String(ownPid) + ": " + line + "\\n");
132200
+ } catch (error) {
132201
+ // Nowhere left to report a failed log write to; the process still has to end.
132202
+ }
132203
+ };
132204
+ const spawnReplacement = () => {
132205
+ if (respawn === undefined || logFile === undefined) return;
132206
+ const servedMs = Date.now() - startedAt;
132207
+ if (servedMs < respawnAfterServingMs) {
132208
+ log("the door served for " + String(servedMs) + "ms before stalling, less than the " + String(respawnAfterServingMs) + "ms it must have served to be replaced; leaving the next launch to start one");
132209
+ return;
132210
+ }
132211
+ try {
132212
+ const out = fs.openSync(logFile, "a");
132213
+ const child = require("node:child_process").spawn(respawn.command, respawn.args, { detached: true, stdio: ["ignore", out, out], env: Object.assign({}, respawn.env, { [awaitPidEnv]: String(ownPid) }) });
132214
+ child.unref();
132215
+ fs.closeSync(out);
132216
+ log("started replacement door " + String(child.pid) + ", which binds once this process is gone");
132217
+ } catch (error) {
132218
+ log("could not start a replacement door: " + (error instanceof Error ? error.message : String(error)));
132219
+ }
132220
+ };
131109
132221
  const timer = setInterval(() => {
131110
132222
  if (stopped) return;
131111
132223
  const now = Date.now();
@@ -131120,6 +132232,8 @@ const timer = setInterval(() => {
131120
132232
  if (now - lastChangeAt >= boundMs) {
131121
132233
  const message = "the front door's event loop did not run for " + String(now - lastChangeAt) + "ms; its watchdog ended the process so the next launch starts a fresh door on the same ports";
131122
132234
  record(message);
132235
+ log(message);
132236
+ spawnReplacement();
131123
132237
  stopped = true;
131124
132238
  clearInterval(timer);
131125
132239
  if (action === "kill-process") {
@@ -131142,7 +132256,7 @@ function startThreadWatchdog(params) {
131142
132256
  const counter = new Int32Array(shared);
131143
132257
  const worker = new import_node_worker_threads2.Worker(WATCHDOG_SOURCE, {
131144
132258
  eval: true,
131145
- workerData: { shared, boundMs: params.boundMs, checkEveryMs: params.checkEveryMs, stateFile: params.stateFile, ownPid: params.ownPid, action: params.action }
132259
+ workerData: { shared, boundMs: params.boundMs, checkEveryMs: params.checkEveryMs, stateFile: params.stateFile, ownPid: params.ownPid, action: params.action, logFile: params.logFile, respawn: params.respawn, respawnAfterServingMs: params.respawnAfterServingMs, awaitPidEnv: DOOR_AWAIT_PID_ENV }
131146
132260
  });
131147
132261
  worker.unref();
131148
132262
  worker.on("message", (message) => {
@@ -131270,6 +132384,13 @@ function createRealQuotaRefresher(params) {
131270
132384
 
131271
132385
  // src/frontdoor/commands.ts
131272
132386
  init_store2();
132387
+ function respawnInvocation(paths) {
132388
+ const env = {};
132389
+ for (const [name, value2] of Object.entries({ ...process.env, AGENT_SHIM_HOME: paths.root })) {
132390
+ env[name] = value2;
132391
+ }
132392
+ return { ...selfInvocation(["__frontdoor-supervisor"]), env };
132393
+ }
131273
132394
  function appendLog(paths, line) {
131274
132395
  import_node_fs19.default.mkdirSync(paths.logsDir, { recursive: true });
131275
132396
  import_node_fs19.default.appendFileSync(paths.frontdoorLogPath, `${(/* @__PURE__ */ new Date()).toISOString()} ${line}
@@ -131312,8 +132433,8 @@ function realFrontDoorSupervisorPorts(paths) {
131312
132433
  };
131313
132434
  const rcSelfHostSurface = rcSelfHost ? createRcSelfHostSurface({
131314
132435
  now: () => Date.now(),
131315
- newUuid: import_node_crypto21.randomUUID,
131316
- randomToken: () => (0, import_node_crypto21.randomBytes)(MINTED_TOKEN_RANDOM_BYTES).toString("base64url"),
132436
+ newUuid: import_node_crypto23.randomUUID,
132437
+ randomToken: () => (0, import_node_crypto23.randomBytes)(MINTED_TOKEN_RANDOM_BYTES).toString("base64url"),
131317
132438
  credentialRecord: () => readRcSelfHostRecord(realFarmFs, paths.frontdoorDir),
131318
132439
  webFetch: realRcWebFetch({ allowPrivate: rcWebFetchAllowsPrivateFromEnv(process.env) }),
131319
132440
  log
@@ -131336,7 +132457,7 @@ function realFrontDoorSupervisorPorts(paths) {
131336
132457
  saveSequenceNum: rcCredentialStore.writeCursor,
131337
132458
  dial: rcSelfHost ? lateRcStreamDial(rcSelfHostDialTarget) : realRcStreamDial(),
131338
132459
  fanout: rcFanout,
131339
- newClientId: import_node_crypto21.randomUUID,
132460
+ newClientId: import_node_crypto23.randomUUID,
131340
132461
  backoffMs: RC_STREAM_BACKOFF_MS,
131341
132462
  sleep: async (ms2) => {
131342
132463
  await new Promise((resolve2) => {
@@ -131348,7 +132469,7 @@ function realFrontDoorSupervisorPorts(paths) {
131348
132469
  }
131349
132470
  });
131350
132471
  const routingSnapshots = /* @__PURE__ */ new Map();
131351
- const rcControlToken = (0, import_node_crypto21.randomUUID)();
132472
+ const rcControlToken = (0, import_node_crypto23.randomUUID)();
131352
132473
  const resolveRoute = rcObservingResolver(
131353
132474
  createProviderRouteResolver({
131354
132475
  fs: realFsPort,
@@ -131464,9 +132585,9 @@ function realFrontDoorSupervisorPorts(paths) {
131464
132585
  now: () => Date.now(),
131465
132586
  headroomSocket: () => headroomSocketTarget(realFarmFs, realHeadroomSocketTrust, paths),
131466
132587
  // The per-generation capability the direct listener demands: held only in this process's memory, so a loopback process that discovers the direct port still cannot use it.
131467
- hopSecret: (0, import_node_crypto21.randomUUID)(),
132588
+ hopSecret: (0, import_node_crypto23.randomUUID)(),
131468
132589
  headroomDecision,
131469
- custody: createCredentialCustody(() => (0, import_node_crypto21.randomUUID)()),
132590
+ custody: createCredentialCustody(() => (0, import_node_crypto23.randomUUID)()),
131470
132591
  log
131471
132592
  });
131472
132593
  const onListenerError = (name) => (error63) => {
@@ -131489,9 +132610,9 @@ function realFrontDoorSupervisorPorts(paths) {
131489
132610
  startProviderListener: async (preferredPort) => {
131490
132611
  const authority = loadCa();
131491
132612
  const rcDial = rcSelfHost ? lateRcEventDial(rcSelfHostDialTarget) : realRcEventDial();
131492
- const rcInject = async (sessionId, text2) => await injectRcUserMessage({ credentialOf: rcTracker.credentialOf, noteSequenceNums: rcTracker.noteSequenceNums, dial: rcDial, newUuid: import_node_crypto21.randomUUID }, sessionId, text2);
132613
+ const rcInject = async (sessionId, text2) => await injectRcUserMessage({ credentialOf: rcTracker.credentialOf, noteSequenceNums: rcTracker.noteSequenceNums, dial: rcDial, newUuid: import_node_crypto23.randomUUID }, sessionId, text2);
131493
132614
  const rcAnswer = async (sessionId, requestId, decision) => await answerRcControlRequest({ credentialOf: rcTracker.credentialOf, pendingOf: (id2) => rcTracker.pendingOf(id2), completePending: rcTracker.completePending, noteSequenceNums: rcTracker.noteSequenceNums, dial: rcDial }, sessionId, requestId, decision);
131494
- const rcControlRequestDeps = { credentialOf: rcTracker.credentialOf, noteSequenceNums: rcTracker.noteSequenceNums, dial: rcDial, newUuid: import_node_crypto21.randomUUID };
132615
+ const rcControlRequestDeps = { credentialOf: rcTracker.credentialOf, noteSequenceNums: rcTracker.noteSequenceNums, dial: rcDial, newUuid: import_node_crypto23.randomUUID };
131495
132616
  const rcInterrupt = async (sessionId) => await interruptRcSession(rcControlRequestDeps, sessionId);
131496
132617
  const rcSetModel = async (sessionId, model) => await setRcSessionModel(rcControlRequestDeps, sessionId, model);
131497
132618
  const rcSetPermissionMode = async (sessionId, mode) => await setRcSessionPermissionMode(rcControlRequestDeps, sessionId, mode);
@@ -131590,7 +132711,7 @@ function realFrontDoorSupervisorPorts(paths) {
131590
132711
  },
131591
132712
  startConnectListener: async (preferredPort) => {
131592
132713
  const wantedTransparentPort = process.env.AGENT_SHIM_TRANSPARENT_SURFACE === void 0 ? void 0 : Number(process.env.AGENT_SHIM_TRANSPARENT_SURFACE);
131593
- const transparentCapability = wantedTransparentPort === void 0 || Number.isNaN(wantedTransparentPort) ? void 0 : (0, import_node_crypto21.randomUUID)();
132714
+ const transparentCapability = wantedTransparentPort === void 0 || Number.isNaN(wantedTransparentPort) ? void 0 : (0, import_node_crypto23.randomUUID)();
131594
132715
  if (transparentCapability !== void 0) {
131595
132716
  writeFrontDoorSession(realFarmFs, paths.frontdoorSessionsDir, { pid: process.pid, startedAt: Date.now(), token: transparentCapability });
131596
132717
  }
@@ -131663,7 +132784,16 @@ function realFrontDoorSupervisorPorts(paths) {
131663
132784
  return { port: handle.port, close: handle.close };
131664
132785
  },
131665
132786
  closeRcStreamHub: rcHub.close,
131666
- startWatchdog: () => startThreadWatchdog({ stateFile: paths.frontdoorStateFile, ownPid: process.pid, boundMs: DOOR_STALL_BOUND_MS, checkEveryMs: DOOR_WATCHDOG_CHECK_MS, action: "kill-process" }),
132787
+ startWatchdog: () => startThreadWatchdog({
132788
+ stateFile: paths.frontdoorStateFile,
132789
+ ownPid: process.pid,
132790
+ boundMs: DOOR_STALL_BOUND_MS,
132791
+ checkEveryMs: DOOR_WATCHDOG_CHECK_MS,
132792
+ action: "kill-process",
132793
+ logFile: paths.frontdoorLogPath,
132794
+ respawn: respawnInvocation(paths),
132795
+ respawnAfterServingMs: DOOR_RESPAWN_MIN_SERVING_MS
132796
+ }),
131667
132797
  // The launch lifecycle publisher over the same backbone the typed API serves: the tick's registry facts go in here, and the door's own register, prune and end moments come out as source-tagged events.
131668
132798
  observeLaunchRegistry: createLaunchEventPublisher(doorEvents, () => Date.now()).observe,
131669
132799
  doorHealth,
@@ -131708,14 +132838,24 @@ function registerFrontDoorCommand(program2, deps) {
131708
132838
  registerRcCommand(frontdoor, paths);
131709
132839
  program2.command("__frontdoor-supervisor", { hidden: true }).description("Internal: serve the front-door routing listeners. Started by the launcher; never run by hand.").allowUnknownOption().action(async () => {
131710
132840
  const idleShutdownMinutes = readGlobalConfig(paths)?.frontdoor?.idleShutdownMinutes ?? FRONTDOOR_DEFAULT_IDLE_SHUTDOWN_MINUTES;
131711
- process.on("SIGTERM", () => {
131712
- deps.exit(0);
131713
- });
131714
- process.on("SIGINT", () => {
131715
- deps.exit(0);
131716
- });
132841
+ const supervisorPorts = realFrontDoorSupervisorPorts(paths);
132842
+ const ownPid = process.pid;
132843
+ process.on("exit", (code) => {
132844
+ supervisorPorts.log(`frontdoor ${String(ownPid)}: exiting with code ${String(code)}`);
132845
+ });
132846
+ for (const signal of ["SIGTERM", "SIGINT"]) {
132847
+ process.on(signal, () => {
132848
+ supervisorPorts.log(`frontdoor ${String(ownPid)}: received ${signal}; exiting`);
132849
+ deps.exit(0);
132850
+ });
132851
+ }
132852
+ const awaited = Number(process.env[DOOR_AWAIT_PID_ENV]);
132853
+ Reflect.deleteProperty(process.env, DOOR_AWAIT_PID_ENV);
132854
+ if (Number.isInteger(awaited) && awaited > 0) {
132855
+ await awaitPidExit(awaited, DOOR_STALL_BOUND_MS, supervisorPorts);
132856
+ }
131717
132857
  declareThisProcessTheFrontDoor();
131718
- deps.exit(await runFrontDoorSupervisor(idleShutdownMinutes, realFrontDoorSupervisorPorts(paths)));
132858
+ deps.exit(await runFrontDoorSupervisor(idleShutdownMinutes, supervisorPorts));
131719
132859
  });
131720
132860
  }
131721
132861
 
@@ -141797,7 +142937,7 @@ function registerCompletionCommand(program2) {
141797
142937
  }
141798
142938
 
141799
142939
  // src/credentialCommand.ts
141800
- var import_node_child_process6 = require("node:child_process");
142940
+ var import_node_child_process7 = require("node:child_process");
141801
142941
  init_commandDeps();
141802
142942
  init_cliError();
141803
142943
  init_credential();
@@ -141857,7 +142997,7 @@ function realCommandPorts(deps) {
141857
142997
  cache: createRealCredentialCache(deps.paths.root),
141858
142998
  platform: process.platform,
141859
142999
  now: () => Date.now(),
141860
- ssh: (host, remoteCommand, input2) => (0, import_node_child_process6.spawnSync)("ssh", ["--", host, remoteCommand], { input: input2, stdio: ["pipe", "inherit", "inherit"] }).status
143000
+ ssh: (host, remoteCommand, input2) => (0, import_node_child_process7.spawnSync)("ssh", ["--", host, remoteCommand], { input: input2, stdio: ["pipe", "inherit", "inherit"] }).status
141861
143001
  };
141862
143002
  }
141863
143003
  var REMOTE_ROOT_SCRIPT = 'root="${AGENT_SHIM_HOME:-${CLAUDE_USE_HOME:-}}"; if [ -z "$root" ]; then if [ ! -d "$HOME/.agent-shim" ] && [ -d "$HOME/.claude-use" ]; then root="$HOME/.claude-use"; else root="$HOME/.agent-shim"; fi; fi';
@@ -141994,7 +143134,7 @@ function registerDoctorCommand(program2, deps) {
141994
143134
  var import_node_fs22 = __toESM(require("node:fs"), 1);
141995
143135
  var import_node_http4 = __toESM(require("node:http"), 1);
141996
143136
  var import_node_path54 = __toESM(require("node:path"), 1);
141997
- var import_node_child_process7 = require("node:child_process");
143137
+ var import_node_child_process8 = require("node:child_process");
141998
143138
  init_commandDeps();
141999
143139
  init_realFrontDoorPort();
142000
143140
  init_trust();
@@ -142178,7 +143318,7 @@ async function readyOverSocket(socketPath) {
142178
143318
  }
142179
143319
  var HEADROOM_TOOL_NAME = "headroom-ai";
142180
143320
  function readInstalledHeadroomCommit() {
142181
- const toolDir = (0, import_node_child_process7.spawnSync)("uv", ["tool", "dir"], { encoding: "utf8" });
143321
+ const toolDir = (0, import_node_child_process8.spawnSync)("uv", ["tool", "dir"], { encoding: "utf8" });
142182
143322
  if (toolDir.status !== 0) {
142183
143323
  return void 0;
142184
143324
  }
@@ -142222,7 +143362,7 @@ function realSupervisorPorts(paths) {
142222
143362
  }
142223
143363
  const logFd = import_node_fs22.default.openSync(paths.headroomLogPath, "a");
142224
143364
  try {
142225
- const child = (0, import_node_child_process7.spawn)("headroom", headroomProxyArgs(socketPath, allowlistFile, settings2), {
143365
+ const child = (0, import_node_child_process8.spawn)("headroom", headroomProxyArgs(socketPath, allowlistFile, settings2), {
142226
143366
  detached: true,
142227
143367
  stdio: ["ignore", logFd, logFd],
142228
143368
  env: headroomSpawnEnv(process.env, settings2, trust?.path)
@@ -142262,7 +143402,7 @@ function realSupervisorPorts(paths) {
142262
143402
  },
142263
143403
  ready: readyOverSocket,
142264
143404
  install: (spec) => {
142265
- const result = (0, import_node_child_process7.spawnSync)("uv", ["tool", "install", spec], { encoding: "utf8", timeout: HEADROOM_INSTALL_TIMEOUT_MS });
143405
+ const result = (0, import_node_child_process8.spawnSync)("uv", ["tool", "install", spec], { encoding: "utf8", timeout: HEADROOM_INSTALL_TIMEOUT_MS });
142266
143406
  if (result.error !== void 0) {
142267
143407
  const timedOut = "code" in result.error && result.error.code === "ETIMEDOUT";
142268
143408
  return {
@@ -142279,7 +143419,7 @@ function realSupervisorPorts(paths) {
142279
143419
  return result.status === 0 ? { ok: true } : { ok: false, error: `uv tool install exited ${String(result.status)}` };
142280
143420
  },
142281
143421
  headroomVersion: () => {
142282
- const result = (0, import_node_child_process7.spawnSync)("headroom", ["--version"], { encoding: "utf8" });
143422
+ const result = (0, import_node_child_process8.spawnSync)("headroom", ["--version"], { encoding: "utf8" });
142283
143423
  return result.status === 0 ? result.stdout.trim() : void 0;
142284
143424
  },
142285
143425
  installedCommit: readInstalledHeadroomCommit,
@@ -142671,11 +143811,38 @@ function toProviderView(name, provider) {
142671
143811
  name,
142672
143812
  kind: provider.kind ?? "http",
142673
143813
  displayName: provider.displayName,
142674
- ...isCodexProvider(provider) ? provider.codex === void 0 ? {} : { codex: provider.codex } : { baseUrl: provider.baseUrl },
143814
+ ...isCodexProvider(provider) ? provider.codex === void 0 ? {} : { codex: provider.codex } : isAntigravityProvider(provider) ? provider.antigravity === void 0 ? {} : { antigravity: provider.antigravity } : { baseUrl: provider.baseUrl },
142675
143815
  credential: summariseCredential(provider.credential),
142676
143816
  ...provider.env === void 0 ? {} : { env: provider.env }
142677
143817
  };
142678
143818
  }
143819
+ function antigravityConfigFromOptions(options) {
143820
+ if (options.antigravityMode === void 0 && options.antigravityDefaultModel === void 0 && options.antigravityModel === void 0 && options.antigravityEffort === void 0 && options.antigravityEndpoint === void 0 && options.antigravityProjectId === void 0 && options.antigravityLocation === void 0 && options.antigravityCommand === void 0 && options.antigravitySocket === void 0) {
143821
+ return void 0;
143822
+ }
143823
+ const cloud = options.antigravityEndpoint !== void 0 || options.antigravityProjectId !== void 0 || options.antigravityLocation !== void 0 ? {
143824
+ ...options.antigravityEndpoint === void 0 ? {} : { endpoint: options.antigravityEndpoint },
143825
+ ...options.antigravityProjectId === void 0 ? {} : { projectId: options.antigravityProjectId },
143826
+ ...options.antigravityLocation === void 0 ? {} : { location: options.antigravityLocation }
143827
+ } : void 0;
143828
+ const local = options.antigravityCommand !== void 0 || options.antigravitySocket !== void 0 ? {
143829
+ ...options.antigravityCommand === void 0 ? {} : { command: options.antigravityCommand },
143830
+ ...options.antigravitySocket === void 0 ? {} : { socketPath: options.antigravitySocket }
143831
+ } : void 0;
143832
+ const candidate = {
143833
+ ...options.antigravityMode === void 0 ? {} : { mode: options.antigravityMode },
143834
+ ...options.antigravityDefaultModel === void 0 ? {} : { defaultModel: options.antigravityDefaultModel },
143835
+ ...options.antigravityModel === void 0 ? {} : { models: options.antigravityModel },
143836
+ ...options.antigravityEffort === void 0 ? {} : { effort: options.antigravityEffort },
143837
+ ...cloud === void 0 ? {} : { cloud },
143838
+ ...local === void 0 ? {} : { local }
143839
+ };
143840
+ const parsed = AntigravityProviderConfigSchema.safeParse(candidate);
143841
+ if (!parsed.success) {
143842
+ throw new UsageError(`Invalid antigravity settings: ${parsed.error.issues.map((issue2) => `${issue2.path.join(".")}: ${issue2.message}`).join("; ")}`);
143843
+ }
143844
+ return parsed.data;
143845
+ }
142679
143846
  function codexConfigFromOptions(options) {
142680
143847
  if (options.codexDefaultModel === void 0 && options.codexModel === void 0 && options.codexEffort === void 0 && options.codexLogin === void 0) {
142681
143848
  return void 0;
@@ -142707,8 +143874,9 @@ function registerProviderCommand(program2, deps) {
142707
143874
  new Option("--credential-target <target>", "Where the token goes: bearer sets ANTHROPIC_AUTH_TOKEN (default), apiKey sets ANTHROPIC_API_KEY.").choices(
142708
143875
  PROVIDER_CREDENTIAL_TARGETS
142709
143876
  )
142710
- ).option("--env <KEY=VALUE>", "Extra environment entry for the child (repeatable).", collectStringPair).option("--codex-default-model <model>", "Codex providers: the codex model a request maps to when no tier matches.").option("--codex-model <tier=model>", "Codex providers: the codex model one tier (fable, opus, sonnet or haiku) maps to (repeatable).", collectStringPair).addOption(new Option("--codex-effort <effort>", "Codex providers: the reasoning effort when a request asks for none the backend accepts.").choices(CODEX_EFFORTS)).addOption(new Option("--codex-login <login>", "Codex providers: which login the upstream call uses, the Codex CLI's own login or a Sign in with ChatGPT grant from `agent-shim codex login`.").choices(CODEX_LOGINS)).option("--json", "Print the result as JSON.").action((name, options) => {
143877
+ ).option("--env <KEY=VALUE>", "Extra environment entry for the child (repeatable).", collectStringPair).option("--codex-default-model <model>", "Codex providers: the codex model a request maps to when no tier matches.").option("--codex-model <tier=model>", "Codex providers: the codex model one tier (fable, opus, sonnet or haiku) maps to (repeatable).", collectStringPair).addOption(new Option("--codex-effort <effort>", "Codex providers: the reasoning effort when a request asks for none the backend accepts.").choices(CODEX_EFFORTS)).addOption(new Option("--codex-login <login>", "Codex providers: which login the upstream call uses, the Codex CLI's own login or a Sign in with ChatGPT grant from `agent-shim codex login`.").choices(CODEX_LOGINS)).addOption(new Option("--antigravity-mode <mode>", "Antigravity providers: cloud (direct Gemini/Vertex) or local (ACP daemon).").choices(ANTIGRAVITY_MODES)).option("--antigravity-default-model <model>", "Antigravity providers: the model a request maps to when no tier matches.").option("--antigravity-model <tier=model>", "Antigravity providers: the model one tier (fable, opus, sonnet or haiku) maps to (repeatable).", collectStringPair).addOption(new Option("--antigravity-effort <effort>", "Antigravity providers: reasoning effort.").choices(ANTIGRAVITY_EFFORTS)).option("--antigravity-endpoint <url>", "Antigravity cloud providers: custom API endpoint URL.").option("--antigravity-project-id <id>", "Antigravity cloud providers: Google Cloud project ID (for Vertex AI).").option("--antigravity-location <loc>", "Antigravity cloud providers: Google Cloud location (for Vertex AI).").option("--antigravity-command <cmd...>", "Antigravity local providers: command to spawn ACP server.", collectRepeated).option("--antigravity-socket <path>", "Antigravity local providers: path to existing Unix domain socket.").option("--json", "Print the result as JSON.").action((name, options) => {
142711
143878
  const codex = codexConfigFromOptions(options);
143879
+ const antigravity = antigravityConfigFromOptions(options);
142712
143880
  const created = addProvider(paths, name, {
142713
143881
  ...options.kind === void 0 ? {} : { kind: options.kind },
142714
143882
  displayName: options.displayName,
@@ -142716,7 +143884,8 @@ function registerProviderCommand(program2, deps) {
142716
143884
  sources: options.credential,
142717
143885
  ...options.credentialTarget === void 0 ? {} : { target: options.credentialTarget },
142718
143886
  ...options.env === void 0 ? {} : { env: options.env },
142719
- ...codex === void 0 ? {} : { codex }
143887
+ ...codex === void 0 ? {} : { codex },
143888
+ ...antigravity === void 0 ? {} : { antigravity }
142720
143889
  });
142721
143890
  reportMutation(options.json, { action: "created", kind: "provider", name, value: created }, () => {
142722
143891
  console.log(`Created provider "${name}" (${describeProviderEndpoint(created)}, credential ${describeCredential(created.credential)}).`);
@@ -142728,7 +143897,9 @@ function registerProviderCommand(program2, deps) {
142728
143897
  "agent-shim provider add anthropic-api --display-name Anthropic --base-url https://api.anthropic.com --credential-target apiKey --credential keychain:anthropic-api-key",
142729
143898
  "agent-shim provider add local --display-name Local --base-url http://127.0.0.1:4000 --credential literal:dummy",
142730
143899
  "agent-shim provider add codex --kind codex --display-name Codex --credential literal:codex",
142731
- "agent-shim provider add codex --kind codex --display-name Codex --credential literal:codex --codex-model sonnet=gpt-5.6-sol --codex-effort medium"
143900
+ "agent-shim provider add codex --kind codex --display-name Codex --credential literal:codex --codex-model sonnet=gpt-5.6-sol --codex-effort medium",
143901
+ "agent-shim provider add agy-cloud --kind antigravity --display-name Antigravity --credential env:GEMINI_API_KEY",
143902
+ "agent-shim provider add agy-local --kind antigravity --display-name Antigravity --antigravity-mode local --credential literal:placeholder"
142732
143903
  ]
142733
143904
  );
142734
143905
  const providerSet = provider.command("set <name>").description("Update an existing API provider definition.").option("--display-name <name>", "Replace the human-readable name.").option("--base-url <url>", "Replace the base URL (http providers only).").option(
@@ -142739,20 +143910,22 @@ function registerProviderCommand(program2, deps) {
142739
143910
  new Option("--credential-target <target>", "Where the token goes: bearer sets ANTHROPIC_AUTH_TOKEN, apiKey sets ANTHROPIC_API_KEY.").choices(
142740
143911
  PROVIDER_CREDENTIAL_TARGETS
142741
143912
  )
142742
- ).option("--env <KEY=VALUE>", "Add or replace an environment entry for the child (repeatable).", collectStringPair).option("--unset-env <KEY>", "Remove an environment entry (repeatable).", collectRepeated).option("--codex-default-model <model>", "Codex providers: replace the model a request maps to when no tier matches.").option("--codex-model <tier=model>", "Codex providers: set the codex model one tier maps to (repeatable; other tiers are kept).", collectStringPair).addOption(new Option("--codex-effort <effort>", "Codex providers: replace the default reasoning effort.").choices(CODEX_EFFORTS)).addOption(new Option("--codex-login <login>", "Codex providers: replace which login the upstream call uses.").choices(CODEX_LOGINS));
143913
+ ).option("--env <KEY=VALUE>", "Add or replace an environment entry for the child (repeatable).", collectStringPair).option("--unset-env <KEY>", "Remove an environment entry (repeatable).", collectRepeated).option("--codex-default-model <model>", "Codex providers: replace the model a request maps to when no tier matches.").option("--codex-model <tier=model>", "Codex providers: set the codex model one tier maps to (repeatable; other tiers are kept).", collectStringPair).addOption(new Option("--codex-effort <effort>", "Codex providers: replace the default reasoning effort.").choices(CODEX_EFFORTS)).addOption(new Option("--codex-login <login>", "Codex providers: replace which login the upstream call uses.").choices(CODEX_LOGINS)).addOption(new Option("--antigravity-mode <mode>", "Antigravity providers: cloud (direct Gemini/Vertex) or local (ACP daemon).").choices(ANTIGRAVITY_MODES)).option("--antigravity-default-model <model>", "Antigravity providers: the model a request maps to when no tier matches.").option("--antigravity-model <tier=model>", "Antigravity providers: set the model one tier maps to (repeatable; other tiers are kept).", collectStringPair).addOption(new Option("--antigravity-effort <effort>", "Antigravity providers: reasoning effort.").choices(ANTIGRAVITY_EFFORTS)).option("--antigravity-endpoint <url>", "Antigravity cloud providers: custom API endpoint URL.").option("--antigravity-project-id <id>", "Antigravity cloud providers: Google Cloud project ID (for Vertex AI).").option("--antigravity-location <loc>", "Antigravity cloud providers: Google Cloud location (for Vertex AI).").option("--antigravity-command <cmd...>", "Antigravity local providers: command to spawn ACP server.", collectRepeated).option("--antigravity-socket <path>", "Antigravity local providers: path to existing Unix domain socket.");
142743
143914
  addCredentialCacheOptions(providerSet);
142744
143915
  withExamples(
142745
143916
  providerSet.option("--json", "Print the result as JSON.").action((name, allOptions) => {
142746
143917
  const { json: json2, ...options } = allOptions;
142747
143918
  if (Object.entries(allOptions).every(([key, value2]) => key === "json" || value2 === void 0)) {
142748
143919
  throw new UsageError(
142749
- "Nothing to change: pass --display-name, --base-url, --credential, --credential-target, a --credential-cache option, --env, --unset-env, --codex-default-model, --codex-model, --codex-effort or --codex-login."
143920
+ "Nothing to change: pass --display-name, --base-url, --credential, --credential-target, a --credential-cache option, --env, --unset-env, or codex/antigravity settings."
142750
143921
  );
142751
143922
  }
142752
143923
  const codex = codexConfigFromOptions(options);
143924
+ const antigravity = antigravityConfigFromOptions(options);
142753
143925
  const cache = cacheChange(options, readProvider(paths, name)?.credential.cache);
142754
143926
  const updated = updateProvider(paths, name, {
142755
143927
  ...codex === void 0 ? {} : { codex },
143928
+ ...antigravity === void 0 ? {} : { antigravity },
142756
143929
  ...cache === void 0 ? {} : { cache },
142757
143930
  ...options.displayName === void 0 ? {} : { displayName: options.displayName },
142758
143931
  ...options.baseUrl === void 0 ? {} : { baseUrl: options.baseUrl },
@@ -142770,7 +143943,8 @@ function registerProviderCommand(program2, deps) {
142770
143943
  "agent-shim provider set z --env API_TIMEOUT_MS=600000",
142771
143944
  "agent-shim provider set z --credential op:op://vault/z/credential --credential-cache-ttl 12h",
142772
143945
  "agent-shim provider set anthropic-api --credential-target apiKey",
142773
- "agent-shim provider set codex --codex-model haiku=gpt-5.6-terra"
143946
+ "agent-shim provider set codex --codex-model haiku=gpt-5.6-terra",
143947
+ "agent-shim provider set agy --antigravity-model haiku=gemini-2.5-flash"
142774
143948
  ]
142775
143949
  );
142776
143950
  withExamples(
@@ -142808,6 +143982,12 @@ function registerProviderCommand(program2, deps) {
142808
143982
  console.log(`Codex models: ${CODEX_TIERS.map((tier) => `${tier}=${config2.models[tier]}`).join(", ")}, otherwise ${config2.defaultModel}`);
142809
143983
  console.log(`Codex effort: ${config2.effort}`);
142810
143984
  console.log(`Codex login: ${config2.login}`);
143985
+ } else if (isAntigravityProvider(found)) {
143986
+ const config2 = resolveAntigravityConfig(found.antigravity);
143987
+ console.log(`Antigravity mode: ${config2.mode}`);
143988
+ console.log(`Antigravity models: ${ANTIGRAVITY_TIERS.map((tier) => `${tier}=${config2.models[tier]}`).join(", ")}, otherwise ${config2.defaultModel}`);
143989
+ console.log(`Antigravity effort: ${config2.effort}`);
143990
+ console.log(`Endpoint: ${describeProviderEndpoint(found)}`);
142811
143991
  } else {
142812
143992
  console.log(`Base URL: ${found.baseUrl}`);
142813
143993
  }