github-router 0.3.137 → 0.3.138
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/browser-ext/manifest.json +1 -1
- package/dist/{engine-DnELl87k.js → engine-kSGZBPRK.js} +1 -1
- package/dist/main.js +3 -3
- package/dist/main.js.map +1 -1
- package/dist/{peer-mcp-personas-KHFhxjFn.js → peer-mcp-personas-CThUmeHE.js} +201 -19
- package/dist/peer-mcp-personas-CThUmeHE.js.map +1 -0
- package/package.json +1 -1
- package/dist/peer-mcp-personas-KHFhxjFn.js.map +0 -1
|
@@ -13,7 +13,7 @@ import process$1 from "node:process";
|
|
|
13
13
|
import { execFile, execFileSync, spawn, spawnSync } from "node:child_process";
|
|
14
14
|
import { chmodSync, closeSync, cpSync, existsSync, mkdirSync, openSync, promises, readFileSync, readdirSync, realpathSync, renameSync, rmSync, statSync, unlinkSync, writeFileSync, writeSync } from "node:fs";
|
|
15
15
|
import { fileURLToPath } from "node:url";
|
|
16
|
-
import { Agent } from "undici";
|
|
16
|
+
import { Agent, ProxyAgent } from "undici";
|
|
17
17
|
import { performance } from "node:perf_hooks";
|
|
18
18
|
import { createInterface } from "node:readline";
|
|
19
19
|
import Parser from "web-tree-sitter";
|
|
@@ -1049,7 +1049,7 @@ function collapsePathKeys(env) {
|
|
|
1049
1049
|
|
|
1050
1050
|
//#endregion
|
|
1051
1051
|
//#region src/lib/insecure-tls.ts
|
|
1052
|
-
const IS_BUN = typeof globalThis.Bun !== "undefined";
|
|
1052
|
+
const IS_BUN$1 = typeof globalThis.Bun !== "undefined";
|
|
1053
1053
|
let sharedInsecureDispatcher;
|
|
1054
1054
|
function insecureDispatcher() {
|
|
1055
1055
|
return sharedInsecureDispatcher ??= new Agent({ connect: { rejectUnauthorized: false } });
|
|
@@ -1060,7 +1060,7 @@ function insecureDispatcher() {
|
|
|
1060
1060
|
* `dispatcher`. Exported so BOTH runtime branches are unit-testable under one
|
|
1061
1061
|
* interpreter (the untested Node branch is exactly what shipped broken).
|
|
1062
1062
|
*/
|
|
1063
|
-
function applyInsecureTls(init, isBun = IS_BUN) {
|
|
1063
|
+
function applyInsecureTls(init, isBun = IS_BUN$1) {
|
|
1064
1064
|
if (isBun) init.tls = { rejectUnauthorized: false };
|
|
1065
1065
|
else init.dispatcher = insecureDispatcher();
|
|
1066
1066
|
}
|
|
@@ -1471,6 +1471,37 @@ function stringProp$1(description) {
|
|
|
1471
1471
|
};
|
|
1472
1472
|
}
|
|
1473
1473
|
|
|
1474
|
+
//#endregion
|
|
1475
|
+
//#region src/lib/fleet/mesh-egress-agent.ts
|
|
1476
|
+
const IS_BUN = typeof globalThis.Bun !== "undefined";
|
|
1477
|
+
/** Thrown when a mesh request is attempted under Bun (no Bearer-proxy support). */
|
|
1478
|
+
var MeshEgressUnsupportedRuntimeError = class extends Error {
|
|
1479
|
+
constructor() {
|
|
1480
|
+
super("mesh egress routing is unsupported under Bun (dev runtime): Bun's fetch cannot send a Proxy-Authorization Bearer header. Run the built Node binary (dist/main.js) to drive mesh peers.");
|
|
1481
|
+
this.name = "MeshEgressUnsupportedRuntimeError";
|
|
1482
|
+
}
|
|
1483
|
+
};
|
|
1484
|
+
/**
|
|
1485
|
+
* Attach the egress-proxy mechanism to a fetch init for a single mesh peer request.
|
|
1486
|
+
* Node → a NEW undici `ProxyAgent` dispatcher whose CONNECT carries the Bearer
|
|
1487
|
+
* `Proxy-Authorization`. A new agent per request is intentional: the credential can
|
|
1488
|
+
* rotate when the sidecar restarts, so a cached agent could pin a stale token, and a
|
|
1489
|
+
* per-request agent avoids stashing the credential in longer-lived state. The caller
|
|
1490
|
+
* MUST `close()` the returned agent after the request (it holds a socket pool).
|
|
1491
|
+
*
|
|
1492
|
+
* `isBun` is injectable so BOTH branches are unit-testable under one interpreter.
|
|
1493
|
+
* Under Bun this THROWS {@link MeshEgressUnsupportedRuntimeError} (fail closed).
|
|
1494
|
+
*/
|
|
1495
|
+
function applyMeshEgressProxy(init, meshProxy, isBun = IS_BUN) {
|
|
1496
|
+
if (isBun) throw new MeshEgressUnsupportedRuntimeError();
|
|
1497
|
+
const agent = new ProxyAgent({
|
|
1498
|
+
uri: meshProxy.url,
|
|
1499
|
+
headers: { "Proxy-Authorization": meshProxy.authHeader }
|
|
1500
|
+
});
|
|
1501
|
+
init.dispatcher = agent;
|
|
1502
|
+
return agent;
|
|
1503
|
+
}
|
|
1504
|
+
|
|
1474
1505
|
//#endregion
|
|
1475
1506
|
//#region src/lib/fleet/tunnel-auth.ts
|
|
1476
1507
|
var TunnelAuthError = class extends Error {
|
|
@@ -1722,6 +1753,8 @@ var FleetClient = class {
|
|
|
1722
1753
|
getTunnelToken;
|
|
1723
1754
|
onTunnelAuthInvalidate;
|
|
1724
1755
|
insecureTLS;
|
|
1756
|
+
meshProxy;
|
|
1757
|
+
applyMeshEgress;
|
|
1725
1758
|
constructor(options) {
|
|
1726
1759
|
this.baseUrl = options.url.replace(/\/+$/, "");
|
|
1727
1760
|
this.origin = new URL(this.baseUrl).origin;
|
|
@@ -1733,6 +1766,8 @@ var FleetClient = class {
|
|
|
1733
1766
|
this.getTunnelToken = options.getTunnelToken;
|
|
1734
1767
|
this.onTunnelAuthInvalidate = options.onTunnelAuthInvalidate;
|
|
1735
1768
|
this.insecureTLS = options.insecureTLS === true;
|
|
1769
|
+
this.meshProxy = options.meshProxy;
|
|
1770
|
+
this.applyMeshEgress = options.applyMeshEgress ?? applyMeshEgressProxy;
|
|
1736
1771
|
}
|
|
1737
1772
|
capabilities(signal) {
|
|
1738
1773
|
return this.request("GET", "/api/control/capabilities", void 0, void 0, signal);
|
|
@@ -1810,6 +1845,11 @@ var FleetClient = class {
|
|
|
1810
1845
|
message: "fleet request URL origin did not match the registered instance origin",
|
|
1811
1846
|
retryable: false
|
|
1812
1847
|
});
|
|
1848
|
+
if (this.auth.type === "mesh" && this.meshProxy === void 0) throw new FleetError({
|
|
1849
|
+
code: "MESH_UNCONFIGURED",
|
|
1850
|
+
message: "mesh egress unconfigured or stale: no live loopback egress proxy for this tailnet peer. Start (or restart) the local ai-or-die `--mesh` sidecar so it publishes a fresh mesh/egress.json; this host cannot reach a `.ts.net` peer directly.",
|
|
1851
|
+
retryable: true
|
|
1852
|
+
});
|
|
1813
1853
|
const devtunnelHost = isDevtunnelHost(url.hostname);
|
|
1814
1854
|
const tunnelEligible = this.getTunnelToken !== void 0 && devtunnelHost && url.protocol === "https:";
|
|
1815
1855
|
for (let attempt = 0; attempt < 2; attempt++) {
|
|
@@ -1828,6 +1868,7 @@ var FleetClient = class {
|
|
|
1828
1868
|
...body === void 0 ? {} : { "Content-Type": "application/json" }
|
|
1829
1869
|
};
|
|
1830
1870
|
let response;
|
|
1871
|
+
let meshAgent;
|
|
1831
1872
|
try {
|
|
1832
1873
|
const init = {
|
|
1833
1874
|
method,
|
|
@@ -1837,8 +1878,17 @@ var FleetClient = class {
|
|
|
1837
1878
|
signal
|
|
1838
1879
|
};
|
|
1839
1880
|
if (this.insecureTLS) applyInsecureTls(init);
|
|
1881
|
+
if (this.auth.type === "mesh") {
|
|
1882
|
+
if (this.meshProxy === void 0) throw new FleetError({
|
|
1883
|
+
code: "MESH_UNCONFIGURED",
|
|
1884
|
+
message: "mesh egress unconfigured or stale: refusing a direct fetch to a tailnet peer.",
|
|
1885
|
+
retryable: true
|
|
1886
|
+
});
|
|
1887
|
+
meshAgent = this.applyMeshEgress(init, this.meshProxy);
|
|
1888
|
+
}
|
|
1840
1889
|
response = await this.fetchFn(url.toString(), init);
|
|
1841
1890
|
} catch (err) {
|
|
1891
|
+
await closeQuietly(meshAgent);
|
|
1842
1892
|
if (canRetry && method === "GET") {
|
|
1843
1893
|
this.onTunnelAuthInvalidate();
|
|
1844
1894
|
continue;
|
|
@@ -1846,13 +1896,18 @@ var FleetClient = class {
|
|
|
1846
1896
|
throw this.auth.type === "mesh" ? mapMeshUnreachable(err) : mapNetworkError(err, devtunnelHost);
|
|
1847
1897
|
}
|
|
1848
1898
|
if (!response.ok) {
|
|
1899
|
+
await closeQuietly(meshAgent);
|
|
1849
1900
|
if ((response.status === 401 || response.status === 403) && canRetry) {
|
|
1850
1901
|
this.onTunnelAuthInvalidate();
|
|
1851
1902
|
continue;
|
|
1852
1903
|
}
|
|
1853
1904
|
throw await mapHttpError(response, url.toString());
|
|
1854
1905
|
}
|
|
1855
|
-
|
|
1906
|
+
try {
|
|
1907
|
+
return await response.json();
|
|
1908
|
+
} finally {
|
|
1909
|
+
await closeQuietly(meshAgent);
|
|
1910
|
+
}
|
|
1856
1911
|
}
|
|
1857
1912
|
throw new FleetError({
|
|
1858
1913
|
code: "AUTH_FAILED",
|
|
@@ -1976,19 +2031,31 @@ function detailToSearchString(detail) {
|
|
|
1976
2031
|
}
|
|
1977
2032
|
}
|
|
1978
2033
|
function mapMeshUnreachable(err) {
|
|
2034
|
+
if (err instanceof FleetError) return err;
|
|
2035
|
+
if (err instanceof MeshEgressUnsupportedRuntimeError) return new FleetError({
|
|
2036
|
+
code: "MESH_UNCONFIGURED",
|
|
2037
|
+
message: err.message,
|
|
2038
|
+
retryable: false
|
|
2039
|
+
});
|
|
1979
2040
|
if (isAbortLike$1(err)) return new FleetError({
|
|
1980
2041
|
code: "TIMEOUT",
|
|
1981
2042
|
message: "fleet mesh peer request timed out or was aborted",
|
|
1982
|
-
retryable: true
|
|
1983
|
-
detail: err
|
|
2043
|
+
retryable: true
|
|
1984
2044
|
});
|
|
1985
2045
|
return new FleetError({
|
|
1986
2046
|
code: "TAILNET_UNREACHABLE",
|
|
1987
|
-
message: `fleet mesh peer unreachable
|
|
1988
|
-
retryable: true
|
|
1989
|
-
detail: err
|
|
2047
|
+
message: `fleet mesh peer unreachable${meshErrorClass(err)} — the request went through the local egress proxy but did not land on the peer. A mesh ACL drops blocked traffic SILENTLY, so the likely cause is the \`tag:aiordie\` ACL (verify the peer permits this node), not a dead instance; also confirm the peer's mesh sidecar is up and serving HTTPS on the tailnet, and that the local egress sidecar is still running.`,
|
|
2048
|
+
retryable: true
|
|
1990
2049
|
});
|
|
1991
2050
|
}
|
|
2051
|
+
function meshErrorClass(err) {
|
|
2052
|
+
if (typeof err !== "object" || err === null) return "";
|
|
2053
|
+
const record = err;
|
|
2054
|
+
const parts = [];
|
|
2055
|
+
if (typeof record.name === "string" && record.name !== "" && record.name !== "Error") parts.push(record.name);
|
|
2056
|
+
if (typeof record.code === "string" && record.code !== "") parts.push(record.code);
|
|
2057
|
+
return parts.length === 0 ? "" : ` (${parts.join(" ")})`;
|
|
2058
|
+
}
|
|
1992
2059
|
function mapNetworkError(err, devtunnelHost = false) {
|
|
1993
2060
|
if (isAbortLike$1(err)) return new FleetError({
|
|
1994
2061
|
code: "TIMEOUT",
|
|
@@ -2028,6 +2095,13 @@ function detailToMessage(detail) {
|
|
|
2028
2095
|
function isAbortLike$1(err) {
|
|
2029
2096
|
return err instanceof Error && (err.name === "AbortError" || err.name === "TimeoutError");
|
|
2030
2097
|
}
|
|
2098
|
+
async function closeQuietly(agent) {
|
|
2099
|
+
if (agent === void 0) return;
|
|
2100
|
+
try {
|
|
2101
|
+
if (typeof agent.destroy === "function") await agent.destroy();
|
|
2102
|
+
else if (typeof agent.close === "function") await agent.close();
|
|
2103
|
+
} catch {}
|
|
2104
|
+
}
|
|
2031
2105
|
|
|
2032
2106
|
//#endregion
|
|
2033
2107
|
//#region src/lib/fleet/registry.ts
|
|
@@ -2266,6 +2340,9 @@ function isNodeErrorCode(err, code) {
|
|
|
2266
2340
|
*/
|
|
2267
2341
|
const DISCOVERY_CACHE_TTL_MS = 5e3;
|
|
2268
2342
|
const PEERS_JSON_MAX_BYTES = 256 * 1024;
|
|
2343
|
+
const EGRESS_TTL_MS = 12e4;
|
|
2344
|
+
const EGRESS_FUTURE_SKEW_MS = 5e3;
|
|
2345
|
+
const EGRESS_JSON_MAX_BYTES = 64 * 1024;
|
|
2269
2346
|
/** The ai-or-die app data dir (NOT github-router's) — mirrors MeshManager's `base`. */
|
|
2270
2347
|
function aiordieAppDir() {
|
|
2271
2348
|
if (process.platform === "win32") {
|
|
@@ -2279,6 +2356,11 @@ function meshPeersFilePath() {
|
|
|
2279
2356
|
if (override && override.trim() !== "") return override.trim();
|
|
2280
2357
|
return nodePath.join(aiordieAppDir(), "mesh", "peers.json");
|
|
2281
2358
|
}
|
|
2359
|
+
function meshEgressFilePath() {
|
|
2360
|
+
const override = process.env.GH_ROUTER_FLEET_EGRESS_FILE;
|
|
2361
|
+
if (override && override.trim() !== "") return override.trim();
|
|
2362
|
+
return nodePath.join(aiordieAppDir(), "mesh", "egress.json");
|
|
2363
|
+
}
|
|
2282
2364
|
function meshDiscoveryDisabled() {
|
|
2283
2365
|
return process.env.GH_ROUTER_FLEET_DISCOVERY === "0";
|
|
2284
2366
|
}
|
|
@@ -2347,16 +2429,104 @@ function toInfo(instance) {
|
|
|
2347
2429
|
url: instance.url
|
|
2348
2430
|
};
|
|
2349
2431
|
}
|
|
2432
|
+
function defaultPidAlive(pid) {
|
|
2433
|
+
try {
|
|
2434
|
+
process.kill(pid, 0);
|
|
2435
|
+
return true;
|
|
2436
|
+
} catch (err) {
|
|
2437
|
+
return typeof err === "object" && err !== null && err.code === "EPERM";
|
|
2438
|
+
}
|
|
2439
|
+
}
|
|
2440
|
+
function validLoopbackHttpUrl(raw) {
|
|
2441
|
+
if (typeof raw !== "string" || raw.trim() === "") return void 0;
|
|
2442
|
+
let url;
|
|
2443
|
+
try {
|
|
2444
|
+
url = new URL(raw.trim());
|
|
2445
|
+
} catch {
|
|
2446
|
+
return;
|
|
2447
|
+
}
|
|
2448
|
+
if (url.protocol !== "http:") return void 0;
|
|
2449
|
+
if (url.username !== "" || url.password !== "") return void 0;
|
|
2450
|
+
if (url.pathname !== "" && url.pathname !== "/" || url.search !== "" || url.hash !== "") return void 0;
|
|
2451
|
+
if (url.port === "") return void 0;
|
|
2452
|
+
const host = url.hostname.replace(/^\[/, "").replace(/\]$/, "").toLowerCase();
|
|
2453
|
+
if (host !== "127.0.0.1" && host !== "::1") return void 0;
|
|
2454
|
+
return `http://${host === "::1" ? "[::1]" : host}:${url.port}`;
|
|
2455
|
+
}
|
|
2456
|
+
function validEgressToken(raw) {
|
|
2457
|
+
if (typeof raw !== "string" || raw === "") return void 0;
|
|
2458
|
+
if (/[\s\u0000-\u001f\u007f\u0080-\u009f]/.test(raw)) return void 0;
|
|
2459
|
+
return raw;
|
|
2460
|
+
}
|
|
2461
|
+
/**
|
|
2462
|
+
* Read + validate the sidecar's `mesh/egress.json` into a {@link FleetMeshProxy}.
|
|
2463
|
+
* Best-effort like {@link readMeshPeers}: NEVER throws — a missing / unreadable /
|
|
2464
|
+
* oversized / malformed / stale / dead-pid file yields `undefined`. The returned
|
|
2465
|
+
* `authHeader` is a credential: it lives only here and in the ProxyAgent header,
|
|
2466
|
+
* never in `FleetInstanceInfo` / logs / errors.
|
|
2467
|
+
*/
|
|
2468
|
+
async function readMeshEgress(options = {}) {
|
|
2469
|
+
if (meshDiscoveryDisabled()) return void 0;
|
|
2470
|
+
const readFileFn = options.readFileFn ?? ((p) => fs.readFile(p, "utf8"));
|
|
2471
|
+
const now = options.now ?? (() => Date.now());
|
|
2472
|
+
const pidAlive = options.pidAlive ?? defaultPidAlive;
|
|
2473
|
+
let raw;
|
|
2474
|
+
try {
|
|
2475
|
+
raw = await readFileFn(meshEgressFilePath());
|
|
2476
|
+
} catch {
|
|
2477
|
+
return;
|
|
2478
|
+
}
|
|
2479
|
+
if (typeof raw !== "string") return void 0;
|
|
2480
|
+
if (Buffer.byteLength(raw, "utf8") > EGRESS_JSON_MAX_BYTES) return void 0;
|
|
2481
|
+
let parsed;
|
|
2482
|
+
try {
|
|
2483
|
+
parsed = JSON.parse(raw);
|
|
2484
|
+
} catch {
|
|
2485
|
+
return;
|
|
2486
|
+
}
|
|
2487
|
+
if (typeof parsed !== "object" || parsed === null || Array.isArray(parsed)) return void 0;
|
|
2488
|
+
if (parsed.version !== 1) return void 0;
|
|
2489
|
+
const url = validLoopbackHttpUrl(parsed.url);
|
|
2490
|
+
if (url === void 0) return void 0;
|
|
2491
|
+
const token = validEgressToken(parsed.token);
|
|
2492
|
+
if (token === void 0) return void 0;
|
|
2493
|
+
if (typeof parsed.pid !== "number" || !Number.isInteger(parsed.pid) || parsed.pid <= 0) return void 0;
|
|
2494
|
+
let alive;
|
|
2495
|
+
try {
|
|
2496
|
+
alive = pidAlive(parsed.pid);
|
|
2497
|
+
} catch {
|
|
2498
|
+
return;
|
|
2499
|
+
}
|
|
2500
|
+
if (!alive) return void 0;
|
|
2501
|
+
if (typeof parsed.updatedAt !== "number" || !Number.isFinite(parsed.updatedAt)) return void 0;
|
|
2502
|
+
let age;
|
|
2503
|
+
try {
|
|
2504
|
+
age = now() - parsed.updatedAt;
|
|
2505
|
+
} catch {
|
|
2506
|
+
return;
|
|
2507
|
+
}
|
|
2508
|
+
if (!Number.isFinite(age)) return void 0;
|
|
2509
|
+
if (age > EGRESS_TTL_MS || age < -EGRESS_FUTURE_SKEW_MS) return void 0;
|
|
2510
|
+
return {
|
|
2511
|
+
url,
|
|
2512
|
+
authHeader: `Bearer ${token}`
|
|
2513
|
+
};
|
|
2514
|
+
}
|
|
2350
2515
|
/**
|
|
2351
2516
|
* Registry that merges a static `fleet.json` registry with mesh discovery. Static
|
|
2352
2517
|
* ALWAYS wins on an id collision (a discovered peer sharing a static id is dropped
|
|
2353
2518
|
* — never overwrites a configured instance, never merges auth across sources).
|
|
2354
2519
|
* Discovery is cached briefly so a fan-out doesn't re-read the file per call, and a
|
|
2355
2520
|
* failed discovery read leaves the static set untouched.
|
|
2521
|
+
*
|
|
2522
|
+
* The mesh egress proxy (from `egress.json`) is read in the SAME cached window and
|
|
2523
|
+
* attached to EVERY discovered mesh peer — the egress is per-conductor/self, shared
|
|
2524
|
+
* by all peers on this tailnet. Static bearer instances never carry one.
|
|
2356
2525
|
*/
|
|
2357
2526
|
var MergedFleetRegistry = class {
|
|
2358
2527
|
staticRegistry;
|
|
2359
2528
|
discover;
|
|
2529
|
+
discoverEgress;
|
|
2360
2530
|
cache;
|
|
2361
2531
|
inflight;
|
|
2362
2532
|
ttlMs;
|
|
@@ -2364,6 +2534,7 @@ var MergedFleetRegistry = class {
|
|
|
2364
2534
|
constructor(options = {}) {
|
|
2365
2535
|
this.staticRegistry = options.staticRegistry ?? new FleetRegistry();
|
|
2366
2536
|
this.discover = options.discover ?? (() => readMeshPeers());
|
|
2537
|
+
this.discoverEgress = options.discoverEgress ?? (() => readMeshEgress());
|
|
2367
2538
|
this.ttlMs = options.ttlMs ?? DISCOVERY_CACHE_TTL_MS;
|
|
2368
2539
|
this.now = options.now ?? (() => Date.now());
|
|
2369
2540
|
}
|
|
@@ -2372,17 +2543,18 @@ var MergedFleetRegistry = class {
|
|
|
2372
2543
|
if (this.cache && now - this.cache.at < this.ttlMs) return this.cache.peers;
|
|
2373
2544
|
if (this.inflight) return this.inflight;
|
|
2374
2545
|
this.inflight = (async () => {
|
|
2375
|
-
|
|
2376
|
-
|
|
2377
|
-
|
|
2378
|
-
|
|
2379
|
-
|
|
2380
|
-
|
|
2546
|
+
const [peersResult, egressResult] = await Promise.allSettled([this.discover(), this.discoverEgress()]);
|
|
2547
|
+
const peers = peersResult.status === "fulfilled" ? peersResult.value : [];
|
|
2548
|
+
const egress = egressResult.status === "fulfilled" ? egressResult.value : void 0;
|
|
2549
|
+
const withEgress = egress === void 0 ? peers : peers.map((peer) => peer.auth.type === "mesh" ? {
|
|
2550
|
+
...peer,
|
|
2551
|
+
meshProxy: egress
|
|
2552
|
+
} : peer);
|
|
2381
2553
|
this.cache = {
|
|
2382
2554
|
at: this.now(),
|
|
2383
|
-
peers
|
|
2555
|
+
peers: withEgress
|
|
2384
2556
|
};
|
|
2385
|
-
return
|
|
2557
|
+
return withEgress;
|
|
2386
2558
|
})().finally(() => {
|
|
2387
2559
|
this.inflight = void 0;
|
|
2388
2560
|
});
|
|
@@ -2445,6 +2617,12 @@ function createFleetTools(options = {}) {
|
|
|
2445
2617
|
return defaultRegistry;
|
|
2446
2618
|
}
|
|
2447
2619
|
function clientFor(instance) {
|
|
2620
|
+
if (instance.auth.type === "mesh") return options.createClient ? options.createClient(instance) : new FleetClient({
|
|
2621
|
+
url: instance.url,
|
|
2622
|
+
auth: instance.auth,
|
|
2623
|
+
fetchFn: options.fetchFn,
|
|
2624
|
+
meshProxy: instance.meshProxy
|
|
2625
|
+
});
|
|
2448
2626
|
const key = `${instance.id}\0${instance.url}\0${instance.auth.type}\0${instance.token}\0${instance.tunnelId ?? ""}\0${instance.tunnelToken ?? ""}\0${instance.insecureTLS === true ? "1" : "0"}`;
|
|
2449
2627
|
const existing = clients.get(key);
|
|
2450
2628
|
if (existing) return existing;
|
|
@@ -2930,6 +3108,8 @@ function fleetProbeHint(code) {
|
|
|
2930
3108
|
case "RELAY_ERROR": return "tunnel relay returned an error; the host may be down, restarting, or under load";
|
|
2931
3109
|
case "TIMEOUT": return "no response before the probe deadline; the host may be slow or the tunnel may have no host";
|
|
2932
3110
|
case "UNREACHABLE": return "could not connect (DNS or connection failure); check the instance url";
|
|
3111
|
+
case "MESH_UNCONFIGURED": return "mesh egress unconfigured or stale; (re)start the local ai-or-die --mesh sidecar so it publishes a fresh mesh/egress.json";
|
|
3112
|
+
case "TAILNET_UNREACHABLE": return "reached the local egress proxy but the request did not land on the tailnet peer; likely the tag:aiordie ACL, or the peer's sidecar is down";
|
|
2933
3113
|
default: return;
|
|
2934
3114
|
}
|
|
2935
3115
|
}
|
|
@@ -2944,7 +3124,9 @@ function isFleetErrorCode(code) {
|
|
|
2944
3124
|
case "NO_HOST":
|
|
2945
3125
|
case "RELAY_ERROR":
|
|
2946
3126
|
case "BAD_REQUEST":
|
|
2947
|
-
case "RATE_LIMITED":
|
|
3127
|
+
case "RATE_LIMITED":
|
|
3128
|
+
case "TAILNET_UNREACHABLE":
|
|
3129
|
+
case "MESH_UNCONFIGURED": return true;
|
|
2948
3130
|
default: return false;
|
|
2949
3131
|
}
|
|
2950
3132
|
}
|
|
@@ -22915,4 +23097,4 @@ async function runStandInToolCall(args, signal) {
|
|
|
22915
23097
|
|
|
22916
23098
|
//#endregion
|
|
22917
23099
|
export { readIteratorWithTimeout as $, state as $t, DEFAULT_MODEL as A, generateRandomPort as At, toolbeltSkipSet as B, filterBetaHeader as Bt, repoRoot as C, toolbeltPathOverride as Ct, resolveSealedGate as D, DEFAULT_PORT as Dt, trustRepo as E, DEFAULT_CODEX_MODEL_FALLBACKS as Et, runWorkerAgent as F, setupGitHubToken as Ft, ADVISOR_INTERNAL_TOOL_NAME as G, getModels as Gt, TOOLBELT_TOOLS$1 as H, resolveCodexModel as Ht, withNoOutputRetry as I, tryRefreshAndRetry as It, injectAdvisorTool as J, forwardError as Jt, ADVISOR_TOOL_INSTRUCTIONS as K, fetchWithTransientRetry as Kt, availableToolCommands as L, cacheCopilotVersion as Lt, PLAN_DEFAULT_MODEL as M, getPackageVersion as Mt, REVIEW_DEFAULT_MODEL as N, withInstallLock as Nt, liveExec as O, UPSTREAM_FETCH_TIMEOUT_MS as Ot, appendPlanReminder as P, setupCopilotToken as Pt, logStreamError as Q, githubHeaders as Qt, buildToolbeltAwareness as R, cacheModels as Rt, repoFingerprint as S, collapsePathKeys as St, stopReviewStateDir as T, DEFAULT_CODEX_MODEL as Tt, assetFor as U, resolveModel as Ut, vscodeRipgrepPath as V, isNullish as Vt, searchWeb as W, sleep as Wt, buildOpenAIErrorEvent as X, copilotBaseUrl as Xt, isAdvisorRequested as Y, GITHUB_API_BASE_URL as Yt, isControllerClosedError as Z, copilotHeaders as Zt, fileBaselineStore as _, provisionAndIndexColbert as _t, buildPeerAwarenessSnippet as a, standInToolEnabled as at, fileReviewDebounce as b, shouldUseInsecureTls as bt, buildSessionBindHookCommand as c, createMessages as ct, decideStopHook as d, createChatCompletions as dt, relayAnthropicStream as et, fileBlockBudget as f, MAX_RESPONSE_BODY_BYTES as ft, stopReviewEnabled as g, hasSupportedBrowserInstalled as gt, stopGateId as h, provisionBrowserAssets as ht, buildAgentPrompt as i, fleetToolsEnabled as it, IMPLEMENT_DEFAULT_MODEL as j, pickClaudeDefault as jt, BROWSE_DEFAULT_MODEL as k, UPSTREAM_INACTIVITY_TIMEOUT_MS as kt, buildStopHookCommand as l, getTokenCount as lt, launchBaselineKey as m, parseJsonOrDiagnose as mt, MCP_GROUPS as n, handleMcpPost as nt, personasFor as o, workerToolsEnabled as ot, injectStopHookIntoSettingsFile as p, readResponseBodyCapped as pt, buildAdvisorStream as q, HTTPError as qt, assertMcpToolSurfaceConsistent as r, browserToolsEnabled as rt, buildArtifactOpenHookCommand as s, countTokens as st, GROUP_META as t, handleMcpDelete as tt, captureLaunchBaseline as u, createResponses as ut, fileFindingsStore as v, extractTarGzMember as vt, stopGateEnabledForRepo as w, DEFAULT_CLAUDE_MODEL_FALLBACKS as wt, isSubagentContext as x, ArtifactClient as xt, fileLastPromptStore as y, extractZipMember as yt, toolbeltEnabled as z, cacheVSCodeVersion as zt };
|
|
22918
|
-
//# sourceMappingURL=peer-mcp-personas-
|
|
23100
|
+
//# sourceMappingURL=peer-mcp-personas-CThUmeHE.js.map
|