@xiaoso/dsh-tool-plus 0.1.16 → 0.1.17-beta.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.
Files changed (109) hide show
  1. package/lib/{abort-DZ54CaKU.mjs → abort-BTblp0Rt.mjs} +2 -2
  2. package/lib/{alibaba-coding-plan-DODpkcqi.mjs → alibaba-coding-plan-t3R4YKCB.mjs} +3 -3
  3. package/lib/{alibaba-token-plan-C6lpKCda.mjs → alibaba-token-plan-CO4djG1y.mjs} +4 -4
  4. package/lib/{alibaba-token-plan-CHGyWOfX.mjs → alibaba-token-plan-CUjYJX0-.mjs} +1 -1
  5. package/lib/{anthropic-Dv_GGX6g.mjs → anthropic-nf7w6so1.mjs} +48 -21
  6. package/lib/{api-key-validation-MnMf_ihX.mjs → api-key-validation-C_tZ7Y9a.mjs} +2 -2
  7. package/lib/behavior-BwvTUtag.mjs +111 -0
  8. package/lib/{browser-render-BZXt548F.mjs → browser-render-BQaEVK_n.mjs} +4 -4
  9. package/lib/{reference-CtvM4zLU.mjs → bundled-references-CrQ4dQcT.mjs} +57 -4
  10. package/lib/cascade-BWjRTD1q.mjs +30265 -0
  11. package/lib/{cline-pass-BT9CBEOj.mjs → cline-pass-Bjm-O8GG.mjs} +2 -2
  12. package/lib/cloudflare-CKXRJ0l9.mjs +37 -0
  13. package/lib/{cloudflare-ai-gateway-DReN6ohJ.mjs → cloudflare-ai-gateway-BpnBSjwV.mjs} +8 -4
  14. package/lib/cloudflare-workers-ai-odj9XswL.mjs +32 -0
  15. package/lib/collapse-_nkb2dn7.mjs +1945 -0
  16. package/lib/{coreweave-C82HrLpb.mjs → coreweave-CGDZOD8-.mjs} +1 -1
  17. package/lib/{coreweave-C68UgRQO.mjs → coreweave-DwffcgW5.mjs} +4 -4
  18. package/lib/cursor-BgOuV7Qf.mjs +794 -0
  19. package/lib/{cursor-_gHHq-Dq.mjs → cursor-CF1iHHbv.mjs} +68 -19
  20. package/lib/{cursor-proto-Cr_WEMuv.mjs → cursor-proto-BuNTjX3L.mjs} +823 -23
  21. package/lib/{devin-QpfTSl9H.mjs → devin-7OEeEb80.mjs} +112 -31
  22. package/lib/{devin-proto-DYhp4Ty6.mjs → devin-proto-C-QreeAv.mjs} +71 -5
  23. package/lib/{dom-DG3sPESc.mjs → dom-BmbZv4v9.mjs} +598 -182
  24. package/lib/{error-O63pC8zg.mjs → error-8LVo7tug.mjs} +725 -104
  25. package/lib/factory-droid-ChhmsGWb.mjs +71 -0
  26. package/lib/{fs-promises-shim-B2YFWkcd.mjs → fs-promises-shim-CANAxFWh.mjs} +10 -1
  27. package/lib/{github-copilot-BMEcw8N1.mjs → github-copilot-QwevdT30.mjs} +4 -4
  28. package/lib/{github-copilot-headers-DnjGEbko.mjs → github-copilot-headers-CAUZ0rUD.mjs} +138 -26
  29. package/lib/{gitlab-duo-DnHqJjFY.mjs → gitlab-duo-DigV7k_o.mjs} +2 -2
  30. package/lib/{google-antigravity-B1mSckrK.mjs → google-antigravity-D-oe0r8A.mjs} +6 -7
  31. package/lib/{google-gemini-cli-DJwThCCn.mjs → google-gemini-cli-CQBHgGJT.mjs} +5 -6
  32. package/lib/{google-oauth-shared-BctLpVUN.mjs → google-oauth-shared-CvgVIUwJ.mjs} +2 -2
  33. package/lib/google-validation-CdvRj4ec.mjs +126 -0
  34. package/lib/id-EJwVLDHE.mjs +2548 -0
  35. package/lib/index.mjs +248 -258
  36. package/lib/{kilo-BEgEwMJQ.mjs → kilo-5r6OffCa.mjs} +2 -2
  37. package/lib/{kimi-T9NldEIJ.mjs → kimi-DOOtbXmm.mjs} +9 -10
  38. package/lib/{launch-BIWNyrBB.mjs → launch-DkAjib7h.mjs} +1 -1
  39. package/lib/{markit-Dvp2JPdT.mjs → markit-CCcyeAds.mjs} +359 -140
  40. package/lib/{models-DnXMYGcJ.mjs → models-DCpDT_im.mjs} +199203 -112275
  41. package/lib/{muse-code-CNvqqAp6.mjs → muse-code-CYf8zj_B.mjs} +5 -5
  42. package/lib/{openai-codex-D5-CyTxa.mjs → openai-codex-Cj-TvSFh.mjs} +13 -10
  43. package/lib/{perplexity-A2PEoGaC.mjs → perplexity-Dh_Qgsmx.mjs} +68 -25
  44. package/lib/{pkce-BYjmugmw.mjs → pkce-DO-jBJLV.mjs} +1 -1
  45. package/lib/pricing-DusBEhwm.mjs +593 -0
  46. package/lib/{readability-uGhqb4GC.mjs → readability-XHK0o3bv.mjs} +287 -27
  47. package/lib/{scrapers-C1ujjV8k.mjs → scrapers-B6PADOVm.mjs} +13 -13
  48. package/lib/slugify-ynYWBIA5.mjs +11 -0
  49. package/lib/snowflake-B_jap6lz.mjs +666 -0
  50. package/lib/snowflake-Cu1ZyOp6.mjs +151 -0
  51. package/lib/{src-AELUUb5U.mjs → src-BhinCSpi.mjs} +1172 -458
  52. package/lib/{stream-AVOoe5Hj.mjs → stream-D2ivg3GH.mjs} +3740 -5311
  53. package/lib/{turndown-D6fof1OX.mjs → turndown-Vya8SavL.mjs} +82 -30
  54. package/lib/types/tools/hashline/native/index.d.ts +2 -2
  55. package/lib/types/tools/hashline/native/policy.d.ts +19 -21
  56. package/lib/types/tools/omp/session/agent-storage.d.ts +3 -3
  57. package/lib/types/tools/shared/bun-named-shim.d.ts +5 -0
  58. package/lib/{types-BLrLohwK.mjs → types-tH1v9uRm.mjs} +2 -2
  59. package/lib/{utils-cZX3f_Ls.mjs → utils-C_Ncya1r.mjs} +1737 -509
  60. package/lib/utils-D2tK38xq.mjs +34006 -0
  61. package/lib/{utils-I4I8azHN.mjs → utils-DrDwmNtu.mjs} +8 -3
  62. package/lib/{xai-oauth-CbeldUSV.mjs → xai-oauth-DLLzX6my.mjs} +4 -4
  63. package/lib/{xiaomi-Dl3VSs04.mjs → xiaomi-CqK-KivK.mjs} +2 -2
  64. package/lib/{zai-FyjGSypr.mjs → zai-DoJ2xPIH.mjs} +2 -2
  65. package/lib/{zip-DRrycScC.mjs → zip-DG1mUV6X.mjs} +1 -1
  66. package/package.json +8 -8
  67. package/lib/amazon-bedrock-Dx0rr9dY.mjs +0 -996
  68. package/lib/anthropic-ClCw0PV_.mjs +0 -3624
  69. package/lib/anthropic-wire-lbGAFzYb.mjs +0 -927
  70. package/lib/azure-openai-responses-WE_bgFWp.mjs +0 -285
  71. package/lib/bundled-references-DY3EJxZV.mjs +0 -56
  72. package/lib/cloudflare-ai-gateway-CrMa97Ap.mjs +0 -44
  73. package/lib/collapse-CkMNRNr7.mjs +0 -2304
  74. package/lib/cursor-C6jaIJDg.mjs +0 -283
  75. package/lib/cursor-D-XZYDf_.mjs +0 -4544
  76. package/lib/deterministic-id-CUEIMSqR.mjs +0 -17
  77. package/lib/devin-ExGIghmx.mjs +0 -69
  78. package/lib/devin-u0ljw5P6.mjs +0 -628
  79. package/lib/effort-BdtQMN-_.mjs +0 -23
  80. package/lib/event-stream-BKEtb45Y.mjs +0 -167
  81. package/lib/gemini-headers-Co9cVvex.mjs +0 -54
  82. package/lib/google-auth-qAN-6DMW.mjs +0 -232
  83. package/lib/google-gemini-cli-B2Aw1S5w.mjs +0 -844
  84. package/lib/google-lTxuq28n.mjs +0 -38
  85. package/lib/google-shared-Y01j9xOr.mjs +0 -856
  86. package/lib/google-validation-BEkNs-Bx.mjs +0 -18
  87. package/lib/google-vertex-DcM-FRC5.mjs +0 -99
  88. package/lib/hosts-00rjRzUD.mjs +0 -203
  89. package/lib/id-AL5obQzR.mjs +0 -71
  90. package/lib/idle-iterator-D0ZXEcUq.mjs +0 -366
  91. package/lib/ollama-6R0oXZks.mjs +0 -574
  92. package/lib/openai-codex-responses-C8bnBWOe.mjs +0 -3232
  93. package/lib/openai-completions-DNr3mUsn.mjs +0 -1430
  94. package/lib/openai-configuration-update-xMYUjaK_.mjs +0 -150
  95. package/lib/openai-reasoning-fallback-Ju-5pSR8.mjs +0 -380
  96. package/lib/openai-responses-CjpafAEr.mjs +0 -861
  97. package/lib/protobuf-BMgDYu_U.mjs +0 -717
  98. package/lib/provider-response-SqKSkkUc.mjs +0 -22
  99. package/lib/proxy-DxvCQOCA.mjs +0 -230
  100. package/lib/request-debug-BwPOqN_j.mjs +0 -183
  101. package/lib/sanitize-text-BCf5KmCf.mjs +0 -33
  102. package/lib/sse-debug-B-tkLCPW.mjs +0 -11
  103. package/lib/stream-markup-healing-CN3RsqG9.mjs +0 -267
  104. package/lib/strict-tool-validation-CBTz1dAA.mjs +0 -105
  105. package/lib/taxonomy-DSIM99rS.mjs +0 -15392
  106. package/lib/thinking-ngMwf_1Y.mjs +0 -336
  107. package/lib/type-guards-CttAANEx.mjs +0 -11
  108. package/lib/utils-CE3DSebh.mjs +0 -11763
  109. package/lib/vision-guard-BCpXWUj3.mjs +0 -77
@@ -0,0 +1,71 @@
1
+ import { installBunShim as __installBunShim } from "./bun-shim.mjs";
2
+ __installBunShim();
3
+ import { _ as LoginCancelledError, h as OAuthError } from "./error-8LVo7tug.mjs";
4
+ import "./utils-C_Ncya1r.mjs";
5
+ import { h as isRecord } from "./cascade-BWjRTD1q.mjs";
6
+ import { l as factoryDroidApiBaseUrl, p as resolveFactoryDroidInferenceRegion } from "./id-EJwVLDHE.mjs";
7
+ //#region node_modules/.pnpm/@oh-my-pi+pi-ai@18.12.6/node_modules/@oh-my-pi/pi-ai/src/registry/oauth/factory-droid.ts
8
+ /** Resolve canonical Factory identity; residency chooses the host, inference scope chooses eligible routes. */
9
+ const attachFactoryDroidRegion = async (credentials, context) => {
10
+ if (context.signal?.aborted) throw new LoginCancelledError("Login cancelled");
11
+ if (!isRecord(context.raw) || typeof context.raw.refresh_token !== "string" || !credentials.refresh) throw new OAuthError("Factory token response missing refresh token", { kind: "validation" });
12
+ const selectedOrg = typeof context.raw.organization_id === "string" ? context.raw.organization_id : context.stored?.activeOrganizationId;
13
+ const sameOrg = !Boolean(credentials.orgId && context.stored?.orgId && credentials.orgId !== context.stored.orgId) && (!selectedOrg || !context.stored?.activeOrganizationId || selectedOrg === context.stored.activeOrganizationId);
14
+ const identity = {
15
+ ...credentials,
16
+ activeOrganizationId: selectedOrg,
17
+ orgId: credentials.orgId ?? (sameOrg ? context.stored?.orgId : void 0),
18
+ region: sameOrg ? context.stored?.region : void 0,
19
+ inferenceRegion: sameOrg ? context.stored?.inferenceRegion : void 0
20
+ };
21
+ const timeout = AbortSignal.timeout(15e3);
22
+ const signal = context.signal ? AbortSignal.any([context.signal, timeout]) : timeout;
23
+ try {
24
+ const response = await context.fetch(`${factoryDroidApiBaseUrl(identity.region)}/api/cli/whoami`, {
25
+ headers: {
26
+ Authorization: `Bearer ${credentials.access}`,
27
+ Accept: "application/json",
28
+ ...identity.orgId ? { "X-Factory-Org-Id": identity.orgId } : {}
29
+ },
30
+ signal
31
+ });
32
+ if (!response.ok && context.phase === "login") throw new OAuthError(`Factory identity check failed (${response.status}): ${await response.text()}`, {
33
+ kind: "validation",
34
+ provider: context.provider,
35
+ status: response.status
36
+ });
37
+ if (response.ok) {
38
+ const body = await response.json();
39
+ if (isRecord(body)) {
40
+ const orgId = typeof body.orgId === "string" && body.orgId ? body.orgId : identity.orgId;
41
+ if (context.phase === "login" && !orgId) throw new OAuthError("Factory login did not resolve an organization", {
42
+ kind: "validation",
43
+ provider: context.provider
44
+ });
45
+ const carried = !orgId || !identity.orgId || orgId === identity.orgId ? identity : void 0;
46
+ const region = body.region === "eu" || body.region === "global" ? body.region : carried?.region;
47
+ const inferenceRegion = body.inferenceRegion === "global" || body.inferenceRegion === "eu" || body.inferenceRegion === "us" ? body.inferenceRegion : resolveFactoryDroidInferenceRegion({
48
+ region,
49
+ inferenceRegion: carried?.inferenceRegion
50
+ });
51
+ return {
52
+ ...identity,
53
+ orgId,
54
+ region,
55
+ inferenceRegion
56
+ };
57
+ }
58
+ }
59
+ } catch (error) {
60
+ if (context.signal?.aborted) throw new LoginCancelledError("Login cancelled");
61
+ if (context.phase === "login") throw error;
62
+ }
63
+ if (context.signal?.aborted) throw new LoginCancelledError("Login cancelled");
64
+ if (context.phase === "login" && !identity.orgId) throw new OAuthError("Factory login did not resolve an organization", {
65
+ kind: "validation",
66
+ provider: context.provider
67
+ });
68
+ return identity;
69
+ };
70
+ //#endregion
71
+ export { attachFactoryDroidRegion };
@@ -7,6 +7,14 @@ var __defProp = Object.defineProperty;
7
7
  var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
8
8
  var __getOwnPropNames = Object.getOwnPropertyNames;
9
9
  var __hasOwnProp = Object.prototype.hasOwnProperty;
10
+ var __esmMin = (fn, res, err) => () => {
11
+ if (err) throw err[0];
12
+ try {
13
+ return fn && (res = fn(fn = 0)), res;
14
+ } catch (e) {
15
+ throw err = [e], e;
16
+ }
17
+ };
10
18
  var __exportAll = (all, no_symbols) => {
11
19
  let target = {};
12
20
  for (var name in all) __defProp(target, name, {
@@ -27,6 +35,7 @@ var __copyProps = (to, from, except, desc) => {
27
35
  return to;
28
36
  };
29
37
  var __reExport = (target, mod, secondTarget) => (__copyProps(target, mod, "default"), secondTarget && __copyProps(secondTarget, mod, "default"));
38
+ var __toCommonJS = (mod) => __hasOwnProp.call(mod, "module.exports") ? mod["module.exports"] : __copyProps(__defProp({}, "__esModule", { value: true }), mod);
30
39
  //#endregion
31
40
  //#region src/tools/shared/fs-promises-shim.ts
32
41
  /**
@@ -55,4 +64,4 @@ async function exists(path) {
55
64
  }
56
65
  }
57
66
  //#endregion
58
- export { fs_promises_shim_exports as n, __exportAll as r, exists as t };
67
+ export { __toCommonJS as a, __exportAll as i, fs_promises_shim_exports as n, __esmMin as r, exists as t };
@@ -1,10 +1,10 @@
1
1
  import { installBunShim as __installBunShim } from "./bun-shim.mjs";
2
2
  __installBunShim();
3
- import { V as ProviderHttpError, f as OAuthError, g as OnPromptRequiredError, m as LoginCancelledError } from "./error-O63pC8zg.mjs";
4
- import { r as getBundledModels } from "./models-DnXMYGcJ.mjs";
5
- import { _ as normalizeCopilotIntegrationId, f as discoverGitHubCopilotApiEndpoint, h as isPublicGitHubHost, o as wrapFetchForCopilotFallback, p as getGitHubCopilotBaseUrl, r as resolveCopilotIntegrationIdOverride, s as COPILOT_API_HEADERS, v as normalizeDomain, y as normalizeGitHubCopilotEnterpriseDomain } from "./github-copilot-headers-DnjGEbko.mjs";
3
+ import { X as ProviderHttpError, _ as LoginCancelledError, h as OAuthError, y as OnPromptRequiredError } from "./error-8LVo7tug.mjs";
4
+ import { r as getBundledModels } from "./models-DCpDT_im.mjs";
5
+ import { _ as isPublicGitHubHost, a as resolveCopilotIntegrationIdOverride, b as normalizeDomain, c as wrapFetchForCopilotFallback, h as getGitHubCopilotBaseUrl, l as COPILOT_API_HEADERS, m as discoverGitHubCopilotApiEndpoint, x as normalizeGitHubCopilotEnterpriseDomain, y as normalizeCopilotIntegrationId } from "./github-copilot-headers-CAUZ0rUD.mjs";
6
6
  import { scheduler } from "node:timers/promises";
7
- //#region node_modules/.pnpm/@oh-my-pi+pi-ai@18.1.17/node_modules/@oh-my-pi/pi-ai/src/registry/oauth/github-copilot.ts
7
+ //#region node_modules/.pnpm/@oh-my-pi+pi-ai@18.12.6/node_modules/@oh-my-pi/pi-ai/src/registry/oauth/github-copilot.ts
8
8
  /**
9
9
  * GitHub Copilot OAuth flow (OpenCode OAuth app, minimal read:user grant).
10
10
  *
@@ -1,9 +1,9 @@
1
1
  import { installBunShim as __installBunShim } from "./bun-shim.mjs";
2
2
  __installBunShim();
3
- import { C as warn, N as $env } from "./src-AELUUb5U.mjs";
4
- import { n as isRecord } from "./type-guards-CttAANEx.mjs";
5
- import "./utils-I4I8azHN.mjs";
6
- //#region node_modules/.pnpm/@oh-my-pi+pi-catalog@18.1.17/node_modules/@oh-my-pi/pi-catalog/src/wire/github-copilot.ts
3
+ import { H as $env, k as warn, p as LRUCache } from "./src-BhinCSpi.mjs";
4
+ import { h as isRecord } from "./cascade-BWjRTD1q.mjs";
5
+ import "./utils-DrDwmNtu.mjs";
6
+ //#region node_modules/.pnpm/@oh-my-pi+pi-catalog@18.12.6/node_modules/@oh-my-pi/pi-catalog/src/wire/github-copilot.ts
7
7
  const COPILOT_CLI_USER_AGENT = `copilot/1.0.82`;
8
8
  /** Headers sent by Copilot CLI to GitHub API and OAuth endpoints. */
9
9
  const COPILOT_GITHUB_HEADERS = { "User-Agent": COPILOT_CLI_USER_AGENT };
@@ -164,7 +164,7 @@ function getGitHubCopilotBaseUrl(enterpriseDomain) {
164
164
  return `https://${normalizedEnterpriseDomain.startsWith("copilot-api.") ? normalizedEnterpriseDomain : `copilot-api.${normalizedEnterpriseDomain}`}`;
165
165
  }
166
166
  //#endregion
167
- //#region node_modules/.pnpm/@oh-my-pi+pi-ai@18.1.17/node_modules/@oh-my-pi/pi-ai/src/providers/github-copilot-headers.ts
167
+ //#region node_modules/.pnpm/@oh-my-pi+pi-ai@18.12.6/node_modules/@oh-my-pi/pi-ai/src/providers/github-copilot-headers.ts
168
168
  function resolveGitHubCopilotBaseUrl(baseUrl, apiKey) {
169
169
  if (!apiKey) return baseUrl;
170
170
  const { enterpriseUrl, apiEndpoint } = parseGitHubCopilotApiKey(apiKey);
@@ -200,37 +200,149 @@ function explicitCopilotIntegrationId(headers) {
200
200
  function resolveCopilotRequestIdentity(headers, explicit, env = $env) {
201
201
  return normalizeCopilotIntegrationId(explicit) ?? normalizeCopilotIntegrationId(explicitCopilotIntegrationId(headers)) ?? resolveCopilotIntegrationIdOverride(env);
202
202
  }
203
+ const copilotWorkingIntegrationCache = new LRUCache({ max: 50 });
203
204
  /**
204
- * Reissue chat-surface Copilot 403s once as the Copilot CLI.
205
+ * Normalize the effective request host for cache isolation. Custom
206
+ * `model.baseUrl` values survive `resolveGitHubCopilotBaseUrl`, so two proxies
207
+ * fronting different org policies must not share a learned identity even when
208
+ * the token envelope matches.
209
+ */
210
+ function normalizeCopilotCacheBaseUrl(baseUrl) {
211
+ const trimmed = baseUrl?.trim().replace(/\/+$/, "") ?? "";
212
+ if (!trimmed) return "";
213
+ try {
214
+ const url = new URL(trimmed);
215
+ return `${url.protocol}//${url.host.toLowerCase()}${url.pathname.replace(/\/+$/, "")}${url.search}${url.hash}`;
216
+ } catch {
217
+ return trimmed.toLowerCase();
218
+ }
219
+ }
220
+ /**
221
+ * Stable cache key for a raw Copilot API key envelope on one effective host.
222
+ * Hashes the bearer with `Bun.hash` (repo-approved hashing API; same
223
+ * credential-scoped pattern as the GitLab Duo and Codex account keys) so token
224
+ * bytes never sit in the map as keys; enterprise/business routing inputs and
225
+ * the normalized effective base URL participate so the same token on two hosts
226
+ * does not share an entry.
227
+ */
228
+ function getCopilotIntegrationCacheKey(apiKeyRaw, baseUrl) {
229
+ if (!apiKeyRaw) return void 0;
230
+ const trimmed = apiKeyRaw.trim();
231
+ if (!trimmed) return void 0;
232
+ const parsed = parseGitHubCopilotApiKey(trimmed);
233
+ if (!parsed.accessToken) return void 0;
234
+ const fingerprint = Bun.hash(parsed.accessToken).toString(36);
235
+ return `${parsed.enterpriseUrl ?? ""}\0${parsed.apiEndpoint ?? ""}\0${normalizeCopilotCacheBaseUrl(baseUrl)}\0${fingerprint}`;
236
+ }
237
+ /** Cached working identity for a cache key, if one was learned. */
238
+ function getCachedCopilotIntegrationId(cacheKey) {
239
+ if (!cacheKey) return void 0;
240
+ return normalizeCopilotIntegrationId(copilotWorkingIntegrationCache.get(cacheKey));
241
+ }
242
+ /**
243
+ * Remember the identity that cleared the identity gate for a credential.
244
+ * Every store refreshes recency, so hot credentials survive eviction.
245
+ */
246
+ function rememberCopilotWorkingIntegrationId(cacheKey, integrationId) {
247
+ const normalized = normalizeCopilotIntegrationId(integrationId);
248
+ if (!cacheKey || !normalized) return;
249
+ copilotWorkingIntegrationCache.set(cacheKey, normalized);
250
+ }
251
+ /** Clear one cached identity, or the whole cache when no key is given. */
252
+ function clearCopilotIntegrationCache(cacheKey) {
253
+ if (cacheKey === void 0) copilotWorkingIntegrationCache.clear();
254
+ else copilotWorkingIntegrationCache.delete(cacheKey);
255
+ }
256
+ /**
257
+ * True when a response is a client-identity denial: HTTP 403, or HTTP 400
258
+ * carrying `code: "model_not_supported"`. Reads a clone so the caller's body
259
+ * stays intact. Unreadable 400s are not denials.
260
+ */
261
+ async function isCopilotIdentityDenied(response) {
262
+ if (response.status === 403) return true;
263
+ if (response.status !== 400) return false;
264
+ try {
265
+ return (await response.clone().json())?.error?.code === "model_not_supported";
266
+ } catch {
267
+ return false;
268
+ }
269
+ }
270
+ /**
271
+ * Reissue Copilot client-identity denials once with the other surface.
205
272
  *
206
273
  * Chat is the default surface (`COPILOT_CHAT_INTEGRATION_ID`) because Business
207
274
  * organizations that gate premium models per client surface commonly allow
208
- * chat while blocking CLI/agentic clients (issue #11372). The retry fires
209
- * only for requests carrying the chat default and only when the caller
210
- * resolved no explicit identity — an explicit choice is never second-guessed.
211
- * The denied body is drained before reissuing, and the retry carries the CLI
212
- * identity so the guard passes it through: at most two requests, never a loop.
275
+ * chat while blocking CLI/agentic clients (issue #11372). Other Business and
276
+ * Enterprise orgs do the opposite and reject the chat identity — as an HTTP 403
277
+ * or, on `api.business.githubcopilot.com`, an HTTP 400 `model_not_supported`
278
+ * (issue #11669). Both denials retry once as the CLI. The retry fires only for
279
+ * requests carrying the chat default and only when the caller resolved no
280
+ * explicit identity — an explicit choice is never second-guessed. The denied
281
+ * body is drained before reissuing, and the retry carries the CLI identity so
282
+ * the guard passes it through: at most two requests, never a loop.
283
+ *
284
+ * When `cacheKey` is set, a 2xx retry remembers its identity via
285
+ * `rememberCopilotWorkingIntegrationId`, so later streams for the same
286
+ * credential start at the working shape. A cached CLI start that is itself
287
+ * denied (stale after an org-policy flip) retries once as chat and relearns.
288
+ * Only a 2xx retry proves its identity — 401s deny every identity equally and
289
+ * 408/429/5xx are transport-retryable (the transport resends the *original*
290
+ * headers), so those must never be recorded as working. Any non-2xx retry
291
+ * clears the entry instead: the next stream rediscovers rather than pinning a
292
+ * shape that just failed.
213
293
  */
214
- function wrapFetchForCopilotFallback(base, enabled, integrationId) {
294
+ function wrapFetchForCopilotFallback(base, enabled, integrationId, cacheKey, cacheSnapshot) {
215
295
  const inner = base ?? fetch;
216
296
  if (!enabled) return inner;
297
+ const cliIntegrationId = COPILOT_CAPI_IDENTITY_HEADERS["Copilot-Integration-Id"];
217
298
  return async (input, init) => {
299
+ const cachedBeforeRequest = cacheSnapshot === void 0 ? getCachedCopilotIntegrationId(cacheKey) : normalizeCopilotIntegrationId(cacheSnapshot);
218
300
  const response = await inner(input, init);
219
- if (response.status !== 403) return response;
301
+ if (response.status !== 403 && response.status !== 400) return response;
220
302
  if (input instanceof Request) return response;
221
303
  if (normalizeCopilotIntegrationId(integrationId) !== void 0) return response;
222
304
  const outgoing = new Headers(init?.headers);
223
- if (outgoing.get("Copilot-Integration-Id") !== "copilot-chat") return response;
224
- try {
225
- await response.arrayBuffer();
226
- } catch {}
227
- warn("GitHub Copilot chat identity denied (HTTP 403); retrying once as the Copilot CLI");
228
- const retryHeaders = new Headers(outgoing);
229
- retryHeaders.set("Copilot-Integration-Id", COPILOT_CAPI_IDENTITY_HEADERS["Copilot-Integration-Id"]);
230
- return inner(input, {
231
- ...init,
232
- headers: retryHeaders
233
- });
305
+ const outgoingId = outgoing.get("Copilot-Integration-Id");
306
+ if (outgoingId === "copilot-chat") {
307
+ if (await isCopilotIdentityDenied(response)) {
308
+ try {
309
+ await response.arrayBuffer();
310
+ } catch {}
311
+ warn(`GitHub Copilot chat identity denied (HTTP ${response.status}); retrying once as the Copilot CLI`);
312
+ const retryHeaders = new Headers(outgoing);
313
+ retryHeaders.set("Copilot-Integration-Id", cliIntegrationId);
314
+ const retry = await inner(input, {
315
+ ...init,
316
+ headers: retryHeaders
317
+ });
318
+ if (cacheKey) {
319
+ if (retry.ok) rememberCopilotWorkingIntegrationId(cacheKey, cliIntegrationId);
320
+ else clearCopilotIntegrationCache(cacheKey);
321
+ }
322
+ return retry;
323
+ }
324
+ return response;
325
+ }
326
+ if (outgoingId === cliIntegrationId && cacheKey) {
327
+ if (cachedBeforeRequest !== cliIntegrationId) return response;
328
+ if (await isCopilotIdentityDenied(response)) {
329
+ try {
330
+ await response.arrayBuffer();
331
+ } catch {}
332
+ warn(`GitHub Copilot CLI identity denied (HTTP ${response.status}); retrying once as ${COPILOT_CHAT_INTEGRATION_ID}`);
333
+ const retryHeaders = new Headers(outgoing);
334
+ retryHeaders.set("Copilot-Integration-Id", COPILOT_CHAT_INTEGRATION_ID);
335
+ const retry = await inner(input, {
336
+ ...init,
337
+ headers: retryHeaders
338
+ });
339
+ if (retry.ok) rememberCopilotWorkingIntegrationId(cacheKey, COPILOT_CHAT_INTEGRATION_ID);
340
+ else clearCopilotIntegrationCache(cacheKey);
341
+ return retry;
342
+ }
343
+ return response;
344
+ }
345
+ return response;
234
346
  };
235
347
  }
236
348
  function inferCopilotInitiator(messages) {
@@ -296,7 +408,7 @@ function buildCopilotDynamicHeaders(params) {
296
408
  "X-Initiator": initiator,
297
409
  "X-Interaction-Type": `conversation-${initiator}`
298
410
  };
299
- headers["Copilot-Integration-Id"] = normalizeCopilotIntegrationId(params.integrationId) ?? "copilot-chat";
411
+ headers["Copilot-Integration-Id"] = normalizeCopilotIntegrationId(params.integrationId) ?? normalizeCopilotIntegrationId(params.cachedIntegrationId) ?? (params.enterpriseUrl ? COPILOT_CAPI_IDENTITY_HEADERS["Copilot-Integration-Id"] : "copilot-chat");
300
412
  if (params.hasImages) headers["Copilot-Vision-Request"] = "true";
301
413
  return {
302
414
  headers,
@@ -309,4 +421,4 @@ function buildCopilotDynamicHeaders(params) {
309
421
  };
310
422
  }
311
423
  //#endregion
312
- export { normalizeCopilotIntegrationId as _, resolveGitHubCopilotBaseUrl as a, parseGitHubCopilotApiKey as b, COPILOT_CHAT_INTEGRATION_ID as c, PERSONAL_GITHUB_COPILOT_BASE_URL as d, discoverGitHubCopilotApiEndpoint as f, mergeCopilotApiHeaders as g, isPublicGitHubHost as h, resolveCopilotRequestIdentity as i, COPILOT_DISCOVERY_HEADERS as l, isPersonalGitHubCopilotBaseUrl as m, hasCopilotVisionInput as n, wrapFetchForCopilotFallback as o, getGitHubCopilotBaseUrl as p, resolveCopilotIntegrationIdOverride as r, COPILOT_API_HEADERS as s, buildCopilotDynamicHeaders as t, COPILOT_GITHUB_HEADERS as u, normalizeDomain as v, normalizeGitHubCopilotEnterpriseDomain as y };
424
+ export { parseGitHubCopilotApiKey as S, isPublicGitHubHost as _, resolveCopilotIntegrationIdOverride as a, normalizeDomain as b, wrapFetchForCopilotFallback as c, COPILOT_DISCOVERY_HEADERS as d, COPILOT_GITHUB_HEADERS as f, isPersonalGitHubCopilotBaseUrl as g, getGitHubCopilotBaseUrl as h, hasCopilotVisionInput as i, COPILOT_API_HEADERS as l, discoverGitHubCopilotApiEndpoint as m, getCachedCopilotIntegrationId as n, resolveCopilotRequestIdentity as o, PERSONAL_GITHUB_COPILOT_BASE_URL as p, getCopilotIntegrationCacheKey as r, resolveGitHubCopilotBaseUrl as s, buildCopilotDynamicHeaders as t, COPILOT_CHAT_INTEGRATION_ID as u, mergeCopilotApiHeaders as v, normalizeGitHubCopilotEnterpriseDomain as x, normalizeCopilotIntegrationId as y };
@@ -1,7 +1,7 @@
1
1
  import { installBunShim as __installBunShim } from "./bun-shim.mjs";
2
2
  __installBunShim();
3
- import { i as clearGitLabDuoDirectAccessCache } from "./stream-AVOoe5Hj.mjs";
4
- //#region node_modules/.pnpm/@oh-my-pi+pi-ai@18.1.17/node_modules/@oh-my-pi/pi-ai/src/registry/oauth/gitlab-duo.ts
3
+ import { t as clearGitLabDuoDirectAccessCache } from "./stream-D2ivg3GH.mjs";
4
+ //#region node_modules/.pnpm/@oh-my-pi+pi-ai@18.12.6/node_modules/@oh-my-pi/pi-ai/src/registry/oauth/gitlab-duo.ts
5
5
  /** GitLab Duo OAuth residue: invalidate direct-access credentials after token rotation. */
6
6
  const gitLabDuoClearCacheHook = async (credentials) => {
7
7
  clearGitLabDuoDirectAccessCache();
@@ -1,14 +1,13 @@
1
1
  import { installBunShim as __installBunShim } from "./bun-shim.mjs";
2
2
  __installBunShim();
3
- import { f as OAuthError, m as LoginCancelledError } from "./error-O63pC8zg.mjs";
4
- import { n as raceWithSignal } from "./abort-DZ54CaKU.mjs";
5
- import { n as getAntigravityUserAgent } from "./gemini-headers-Co9cVvex.mjs";
6
- import { n as formatGoogleValidationRequiredMessage, t as extractGoogleValidationUrl } from "./google-validation-BEkNs-Bx.mjs";
7
- import { n as throwIfLoginCancelled, t as oauthFetch } from "./google-oauth-shared-BctLpVUN.mjs";
3
+ import { _ as LoginCancelledError, h as OAuthError } from "./error-8LVo7tug.mjs";
4
+ import { n as raceWithSignal } from "./abort-BTblp0Rt.mjs";
5
+ import { a as getAntigravityUserAgent, n as formatGoogleValidationRequiredMessage, t as extractGoogleValidationUrl } from "./google-validation-CdvRj4ec.mjs";
6
+ import { n as throwIfLoginCancelled, t as oauthFetch } from "./google-oauth-shared-CvgVIUwJ.mjs";
8
7
  import { type } from "@oh-my-pi/omptype";
9
- //#region node_modules/.pnpm/@oh-my-pi+pi-ai@18.1.17/node_modules/@oh-my-pi/pi-ai/src/registry/oauth/google-antigravity.ts
8
+ //#region node_modules/.pnpm/@oh-my-pi+pi-ai@18.12.6/node_modules/@oh-my-pi/pi-ai/src/registry/oauth/google-antigravity.ts
10
9
  /**
11
- * Antigravity OAuth flow (Gemini 3, Claude, GPT-OSS via Google Cloud)
10
+ * Google Antigravity OAuth flow (Gemini, Claude, GPT-OSS via Google Cloud)
12
11
  * Uses different OAuth credentials than google-gemini-cli for access to additional models.
13
12
  */
14
13
  const CLOUD_CODE_ASSIST_ENDPOINT = "https://daily-cloudcode-pa.googleapis.com";
@@ -1,11 +1,10 @@
1
1
  import { installBunShim as __installBunShim } from "./bun-shim.mjs";
2
2
  __installBunShim();
3
- import { N as $env } from "./src-AELUUb5U.mjs";
4
- import { f as OAuthError } from "./error-O63pC8zg.mjs";
5
- import { r as getGeminiCliHeaders } from "./gemini-headers-Co9cVvex.mjs";
6
- import { n as formatGoogleValidationRequiredMessage, t as extractGoogleValidationUrl } from "./google-validation-BEkNs-Bx.mjs";
7
- import { n as throwIfLoginCancelled, t as oauthFetch } from "./google-oauth-shared-BctLpVUN.mjs";
8
- //#region node_modules/.pnpm/@oh-my-pi+pi-ai@18.1.17/node_modules/@oh-my-pi/pi-ai/src/registry/oauth/google-gemini-cli.ts
3
+ import { H as $env } from "./src-BhinCSpi.mjs";
4
+ import { h as OAuthError } from "./error-8LVo7tug.mjs";
5
+ import { n as formatGoogleValidationRequiredMessage, o as getGeminiCliHeaders, t as extractGoogleValidationUrl } from "./google-validation-CdvRj4ec.mjs";
6
+ import { n as throwIfLoginCancelled, t as oauthFetch } from "./google-oauth-shared-CvgVIUwJ.mjs";
7
+ //#region node_modules/.pnpm/@oh-my-pi+pi-ai@18.12.6/node_modules/@oh-my-pi/pi-ai/src/registry/oauth/google-gemini-cli.ts
9
8
  /**
10
9
  * Gemini CLI OAuth flow (Google Cloud Code Assist)
11
10
  * Standard Gemini models only (gemini-2.0-flash, gemini-2.5-*)
@@ -1,7 +1,7 @@
1
1
  import { installBunShim as __installBunShim } from "./bun-shim.mjs";
2
2
  __installBunShim();
3
- import { f as OAuthError, m as LoginCancelledError } from "./error-O63pC8zg.mjs";
4
- //#region node_modules/.pnpm/@oh-my-pi+pi-ai@18.1.17/node_modules/@oh-my-pi/pi-ai/src/registry/oauth/google-oauth-shared.ts
3
+ import { _ as LoginCancelledError, h as OAuthError } from "./error-8LVo7tug.mjs";
4
+ //#region node_modules/.pnpm/@oh-my-pi+pi-ai@18.12.6/node_modules/@oh-my-pi/pi-ai/src/registry/oauth/google-oauth-shared.ts
5
5
  /**
6
6
  * Shared OAuth flow for Google-style providers (Gemini CLI, Antigravity).
7
7
  *
@@ -0,0 +1,126 @@
1
+ import { installBunShim as __installBunShim } from "./bun-shim.mjs";
2
+ __installBunShim();
3
+ //#region node_modules/.pnpm/@oh-my-pi+pi-catalog@18.12.6/node_modules/@oh-my-pi/pi-catalog/src/wire/gemini-headers.ts
4
+ /**
5
+ * Build a User-Agent string that identifies as Gemini CLI to unlock higher rate limits.
6
+ * Uses the same format as the official Gemini CLI (v0.35+):
7
+ * GeminiCLI/VERSION/MODEL (PLATFORM; ARCH; SURFACE)
8
+ */
9
+ function getGeminiCliUserAgent(modelId = "gemini-3.1-pro-preview") {
10
+ return `GeminiCLI/${process.env.PI_AI_GEMINI_CLI_VERSION || "0.46.0"}/${modelId} (${process.platform === "win32" ? "win32" : process.platform}; ${process.arch === "x64" ? "x64" : process.arch}; terminal)`;
11
+ }
12
+ const getGeminiCliHeaders = (modelId) => ({
13
+ "User-Agent": getGeminiCliUserAgent(modelId),
14
+ "Client-Metadata": "ideType=IDE_UNSPECIFIED,platform=PLATFORM_UNSPECIFIED,pluginType=GEMINI"
15
+ });
16
+ const ANTIGRAVITY_VERSION_MANIFEST_URL = "https://antigravity-hub-auto-updater-974169037036.us-central1.run.app/manifest/latest-arm64-mac.yml";
17
+ const ANTIGRAVITY_VERSION_FETCH_TIMEOUT_MS = 5e3;
18
+ /** Failed manifest lookups are not retried before this delay, so request paths never stall per call. */
19
+ const ANTIGRAVITY_VERSION_RETRY_MS = 6e5;
20
+ let discoveredAntigravityVersion = null;
21
+ let antigravityVersionFetch = null;
22
+ let antigravityVersionFailedAt;
23
+ /** Current Antigravity client version: env override → manifest-discovered → pinned fallback. */
24
+ function getAntigravityVersion() {
25
+ return process.env.PI_AI_ANTIGRAVITY_VERSION || discoveredAntigravityVersion || "2.19.1";
26
+ }
27
+ /**
28
+ * Extracts the client version from an electron-builder update manifest.
29
+ * Returns null when no well-formed `version:` line is present.
30
+ */
31
+ function parseAntigravityManifestVersion(yamlText) {
32
+ for (const line of yamlText.split(/\r?\n/)) {
33
+ const match = /^\s*version\s*:\s*(?:"([^"]*)"|'([^']*)'|([^\s#]+))\s*(?:#.*)?$/.exec(line);
34
+ if (!match) continue;
35
+ const version = (match[1] ?? match[2] ?? match[3] ?? "").trim();
36
+ return /^\d+\.\d+\.\d+$/.test(version) ? version : null;
37
+ }
38
+ return null;
39
+ }
40
+ /**
41
+ * Resolves the latest Antigravity release from the official update manifest.
42
+ * Success is cached for the process lifetime; failures are silent (the pinned
43
+ * fallback stays valid) and suppress further lookups for
44
+ * `ANTIGRAVITY_VERSION_RETRY_MS`. Skipped entirely when PI_AI_ANTIGRAVITY_VERSION is set.
45
+ *
46
+ * The lookup is shared by concurrent callers, so it is bounded only by its own
47
+ * timeout; `signal` ends this caller's wait without cancelling the lookup.
48
+ */
49
+ function ensureAntigravityVersion(fetcher = fetch, signal) {
50
+ if (process.env.PI_AI_ANTIGRAVITY_VERSION || discoveredAntigravityVersion) return Promise.resolve();
51
+ if (!antigravityVersionFetch) {
52
+ if (antigravityVersionFailedAt !== void 0 && Date.now() - antigravityVersionFailedAt < ANTIGRAVITY_VERSION_RETRY_MS) return Promise.resolve();
53
+ antigravityVersionFetch = (async () => {
54
+ try {
55
+ const response = await fetcher(ANTIGRAVITY_VERSION_MANIFEST_URL, {
56
+ headers: {
57
+ "Cache-Control": "no-cache",
58
+ "User-Agent": "electron-builder"
59
+ },
60
+ signal: AbortSignal.timeout(ANTIGRAVITY_VERSION_FETCH_TIMEOUT_MS)
61
+ });
62
+ if (response.ok) discoveredAntigravityVersion = parseAntigravityManifestVersion(await response.text());
63
+ } catch {} finally {
64
+ antigravityVersionFetch = null;
65
+ if (!discoveredAntigravityVersion) antigravityVersionFailedAt = Date.now();
66
+ }
67
+ })();
68
+ }
69
+ const lookup = antigravityVersionFetch;
70
+ if (!signal) return lookup;
71
+ if (signal.aborted) return Promise.resolve();
72
+ const { promise: aborted, resolve } = Promise.withResolvers();
73
+ const onAbort = () => resolve();
74
+ signal.addEventListener("abort", onAbort, { once: true });
75
+ return Promise.race([lookup, aborted]).finally(() => signal.removeEventListener("abort", onAbort));
76
+ }
77
+ /** Antigravity `User-Agent` header value; rebuilt when the discovered version changes. */
78
+ function getAntigravityUserAgent() {
79
+ const version = getAntigravityVersion();
80
+ const cl = process.env.PI_AI_ANTIGRAVITY_CL || "963137146";
81
+ return `antigravity/hub/${version} (aidev_client; os_type=${process.env.PI_AI_ANTIGRAVITY_OS || "darwin"}; arch=${process.env.PI_AI_ANTIGRAVITY_ARCH || "arm64"}; cl=${cl})`;
82
+ }
83
+ const ANTIGRAVITY_MODEL_WIRE_PROFILES = {
84
+ "gemini-3.5-flash-extra-low": {
85
+ modelEnum: "MODEL_PLACEHOLDER_M187",
86
+ maxOutputTokens: 65536
87
+ },
88
+ "gemini-3.5-flash-low": {
89
+ modelEnum: "MODEL_PLACEHOLDER_M20",
90
+ maxOutputTokens: 65536
91
+ },
92
+ "gemini-3-flash-agent": {
93
+ modelEnum: "MODEL_PLACEHOLDER_M132",
94
+ maxOutputTokens: 65536
95
+ },
96
+ "gemini-3.1-pro-low": {
97
+ modelEnum: "MODEL_PLACEHOLDER_M36",
98
+ maxOutputTokens: 65535
99
+ },
100
+ "gemini-pro-agent": {
101
+ modelEnum: "MODEL_PLACEHOLDER_M16",
102
+ maxOutputTokens: 65535
103
+ },
104
+ "claude-sonnet-4-6": { maxOutputTokens: 64e3 },
105
+ "claude-opus-4-6-thinking": { maxOutputTokens: 64e3 }
106
+ };
107
+ function getAntigravityModelWireProfile(wireModelId) {
108
+ return ANTIGRAVITY_MODEL_WIRE_PROFILES[wireModelId];
109
+ }
110
+ //#endregion
111
+ //#region node_modules/.pnpm/@oh-my-pi+pi-ai@18.12.6/node_modules/@oh-my-pi/pi-ai/src/utils/google-validation.ts
112
+ function extractGoogleValidationUrl(errorBody) {
113
+ if (!errorBody.includes("VALIDATION_REQUIRED")) return void 0;
114
+ const start = errorBody.indexOf("{");
115
+ if (start === -1) return void 0;
116
+ try {
117
+ return (JSON.parse(errorBody.slice(start)).error?.details?.find((d) => d.reason === "VALIDATION_REQUIRED" && typeof d.metadata?.validation_url === "string"))?.metadata?.validation_url;
118
+ } catch {
119
+ return;
120
+ }
121
+ }
122
+ function formatGoogleValidationRequiredMessage(validationUrl, nextAction, email) {
123
+ return `Account verification required${email ? ` for ${email}` : ""}. Visit ${validationUrl} to continue, then ${nextAction}.`;
124
+ }
125
+ //#endregion
126
+ export { getAntigravityUserAgent as a, getAntigravityModelWireProfile as i, formatGoogleValidationRequiredMessage as n, getGeminiCliHeaders as o, ensureAntigravityVersion as r, extractGoogleValidationUrl as t };