@blockrun/clawrouter 0.12.253 → 0.12.254
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.js +22 -9
- package/dist/index.js +22 -9
- package/package.json +1 -1
package/dist/cli.js
CHANGED
|
@@ -92320,13 +92320,16 @@ async function proxyRequest(req, res, apiBase, payFetch, options, routerOpts, de
|
|
|
92320
92320
|
const timeoutMs = options.requestTimeoutMs ?? DEFAULT_REQUEST_TIMEOUT_MS;
|
|
92321
92321
|
const globalController = new AbortController();
|
|
92322
92322
|
const timeoutId = setTimeout(() => globalController.abort(), timeoutMs);
|
|
92323
|
+
const clientDisconnected = () => res.destroyed && !res.writableEnded;
|
|
92324
|
+
const abortError = () => clientDisconnected() ? new ClientDisconnectedError() : new Error(`Request timed out after ${timeoutMs}ms`);
|
|
92323
92325
|
const onClientClose = () => {
|
|
92324
|
-
if (!globalController.signal.aborted) {
|
|
92326
|
+
if (!res.writableEnded && !globalController.signal.aborted) {
|
|
92325
92327
|
console.log(`[ClawRouter] Client disconnected \u2014 aborting upstream request`);
|
|
92326
92328
|
globalController.abort();
|
|
92327
92329
|
}
|
|
92328
92330
|
};
|
|
92329
|
-
|
|
92331
|
+
res.on("close", onClientClose);
|
|
92332
|
+
if (res.destroyed) onClientClose();
|
|
92330
92333
|
try {
|
|
92331
92334
|
let modelsToTry;
|
|
92332
92335
|
const excludeList = options.excludeModels ?? loadExcludeList();
|
|
@@ -92385,7 +92388,7 @@ data: [DONE]
|
|
|
92385
92388
|
completed = true;
|
|
92386
92389
|
deduplicator.removeInflight(dedupKey);
|
|
92387
92390
|
clearTimeout(timeoutId);
|
|
92388
|
-
|
|
92391
|
+
res.removeListener("close", onClientClose);
|
|
92389
92392
|
return;
|
|
92390
92393
|
}
|
|
92391
92394
|
const contextExcluded = fullChain.filter((m) => !contextFiltered.includes(m));
|
|
@@ -92484,7 +92487,7 @@ data: [DONE]
|
|
|
92484
92487
|
}
|
|
92485
92488
|
deduplicator.removeInflight(dedupKey);
|
|
92486
92489
|
clearTimeout(timeoutId);
|
|
92487
|
-
|
|
92490
|
+
res.removeListener("close", onClientClose);
|
|
92488
92491
|
return;
|
|
92489
92492
|
}
|
|
92490
92493
|
if (excluded.length > 0) {
|
|
@@ -92515,7 +92518,7 @@ data: [DONE]
|
|
|
92515
92518
|
const tryModel = modelsToTry[i];
|
|
92516
92519
|
const isLastAttempt = i === modelsToTry.length - 1;
|
|
92517
92520
|
if (globalController.signal.aborted) {
|
|
92518
|
-
throw
|
|
92521
|
+
throw abortError();
|
|
92519
92522
|
}
|
|
92520
92523
|
console.log(`[ClawRouter] Trying model ${i + 1}/${modelsToTry.length}: ${tryModel}`);
|
|
92521
92524
|
const perAttemptTimeoutMs = timeoutForModel(tryModel);
|
|
@@ -92535,7 +92538,7 @@ data: [DONE]
|
|
|
92535
92538
|
);
|
|
92536
92539
|
clearTimeout(modelTimeoutId);
|
|
92537
92540
|
if (globalController.signal.aborted) {
|
|
92538
|
-
throw
|
|
92541
|
+
throw abortError();
|
|
92539
92542
|
}
|
|
92540
92543
|
if (!result.success && modelController.signal.aborted && !isLastAttempt) {
|
|
92541
92544
|
console.log(
|
|
@@ -92747,7 +92750,7 @@ data: [DONE]
|
|
|
92747
92750
|
break;
|
|
92748
92751
|
}
|
|
92749
92752
|
clearTimeout(timeoutId);
|
|
92750
|
-
|
|
92753
|
+
res.removeListener("close", onClientClose);
|
|
92751
92754
|
if (heartbeatInterval) {
|
|
92752
92755
|
clearInterval(heartbeatInterval);
|
|
92753
92756
|
heartbeatInterval = void 0;
|
|
@@ -93250,12 +93253,16 @@ data: [DONE]
|
|
|
93250
93253
|
completed = true;
|
|
93251
93254
|
} catch (err) {
|
|
93252
93255
|
clearTimeout(timeoutId);
|
|
93253
|
-
|
|
93256
|
+
res.removeListener("close", onClientClose);
|
|
93254
93257
|
if (heartbeatInterval) {
|
|
93255
93258
|
clearInterval(heartbeatInterval);
|
|
93256
93259
|
heartbeatInterval = void 0;
|
|
93257
93260
|
}
|
|
93258
93261
|
deduplicator.removeInflight(dedupKey);
|
|
93262
|
+
if (err instanceof ClientDisconnectedError || err instanceof Error && err.name === "AbortError" && clientDisconnected()) {
|
|
93263
|
+
console.log(`[ClawRouter] Request cancelled \u2014 client disconnected`);
|
|
93264
|
+
return;
|
|
93265
|
+
}
|
|
93259
93266
|
balanceMonitor.invalidate();
|
|
93260
93267
|
if (err instanceof Error && err.name === "AbortError") {
|
|
93261
93268
|
throw new Error(`Request timed out after ${timeoutMs}ms`, { cause: err });
|
|
@@ -93311,7 +93318,7 @@ data: [DONE]
|
|
|
93311
93318
|
});
|
|
93312
93319
|
}
|
|
93313
93320
|
}
|
|
93314
|
-
var paymentStore, BLOCKRUN_API, BLOCKRUN_SOLANA_API, IMAGE_DIR, AUDIO_DIR, VIDEO_DIR, AUTO_MODEL, ROUTING_PROFILES, FREE_MODELS, FREE_MODEL, MAX_MESSAGES, CONTEXT_LIMIT_KB, HEARTBEAT_INTERVAL_MS, BALANCE_CHECK_TIMEOUT_MS, DEFAULT_REQUEST_TIMEOUT_MS, PER_MODEL_TIMEOUT_MS, REASONING_MODEL_TIMEOUT_MS, REASONING_MODEL_IDS, MAX_FALLBACK_ATTEMPTS, HEALTH_CHECK_TIMEOUT_MS, RATE_LIMIT_COOLDOWN_MS, OVERLOAD_COOLDOWN_MS, PORT_RETRY_ATTEMPTS, PORT_RETRY_DELAY_MS, MODEL_BODY_READ_TIMEOUT_MS, ERROR_BODY_READ_TIMEOUT_MS, rateLimitedModels, overloadedModels, perProviderErrors, BALANCE_CHECK_BUFFER, BALANCE_PREFLIGHT_OUTPUT_TOKEN_CAP, PROVIDER_ERROR_PATTERNS, DEGRADED_RESPONSE_PATTERNS, DEGRADED_LOOP_PATTERNS, VALID_ROLES, ROLE_MAPPINGS, VALID_TOOL_ID_PATTERN, KIMI_BLOCK_RE, KIMI_TOKEN_RE, THINKING_TAG_RE, THINKING_BLOCK_RE, BLOCKRUN_MODEL_BY_ID, IMAGE_PRICING, IMAGE_MODEL_IDS, IMAGE_MODEL_SIZES, IMAGE_MODEL_ALIASES, VIDEO_PRICING, PHONE_PRICING;
|
|
93321
|
+
var paymentStore, BLOCKRUN_API, BLOCKRUN_SOLANA_API, IMAGE_DIR, AUDIO_DIR, VIDEO_DIR, AUTO_MODEL, ROUTING_PROFILES, FREE_MODELS, FREE_MODEL, MAX_MESSAGES, CONTEXT_LIMIT_KB, HEARTBEAT_INTERVAL_MS, BALANCE_CHECK_TIMEOUT_MS, DEFAULT_REQUEST_TIMEOUT_MS, PER_MODEL_TIMEOUT_MS, REASONING_MODEL_TIMEOUT_MS, REASONING_MODEL_IDS, MAX_FALLBACK_ATTEMPTS, HEALTH_CHECK_TIMEOUT_MS, RATE_LIMIT_COOLDOWN_MS, OVERLOAD_COOLDOWN_MS, PORT_RETRY_ATTEMPTS, PORT_RETRY_DELAY_MS, MODEL_BODY_READ_TIMEOUT_MS, ERROR_BODY_READ_TIMEOUT_MS, ClientDisconnectedError, rateLimitedModels, overloadedModels, perProviderErrors, BALANCE_CHECK_BUFFER, BALANCE_PREFLIGHT_OUTPUT_TOKEN_CAP, PROVIDER_ERROR_PATTERNS, DEGRADED_RESPONSE_PATTERNS, DEGRADED_LOOP_PATTERNS, VALID_ROLES, ROLE_MAPPINGS, VALID_TOOL_ID_PATTERN, KIMI_BLOCK_RE, KIMI_TOKEN_RE, THINKING_TAG_RE, THINKING_BLOCK_RE, BLOCKRUN_MODEL_BY_ID, IMAGE_PRICING, IMAGE_MODEL_IDS, IMAGE_MODEL_SIZES, IMAGE_MODEL_ALIASES, VIDEO_PRICING, PHONE_PRICING;
|
|
93315
93322
|
var init_proxy = __esm({
|
|
93316
93323
|
"src/proxy.ts"() {
|
|
93317
93324
|
"use strict";
|
|
@@ -93391,6 +93398,12 @@ var init_proxy = __esm({
|
|
|
93391
93398
|
PORT_RETRY_DELAY_MS = 1e3;
|
|
93392
93399
|
MODEL_BODY_READ_TIMEOUT_MS = 3e5;
|
|
93393
93400
|
ERROR_BODY_READ_TIMEOUT_MS = 3e4;
|
|
93401
|
+
ClientDisconnectedError = class extends Error {
|
|
93402
|
+
constructor() {
|
|
93403
|
+
super("Client disconnected");
|
|
93404
|
+
this.name = "ClientDisconnectedError";
|
|
93405
|
+
}
|
|
93406
|
+
};
|
|
93394
93407
|
rateLimitedModels = /* @__PURE__ */ new Map();
|
|
93395
93408
|
overloadedModels = /* @__PURE__ */ new Map();
|
|
93396
93409
|
perProviderErrors = /* @__PURE__ */ new Map();
|
package/dist/index.js
CHANGED
|
@@ -92140,13 +92140,16 @@ async function proxyRequest(req, res, apiBase, payFetch, options, routerOpts, de
|
|
|
92140
92140
|
const timeoutMs = options.requestTimeoutMs ?? DEFAULT_REQUEST_TIMEOUT_MS;
|
|
92141
92141
|
const globalController = new AbortController();
|
|
92142
92142
|
const timeoutId = setTimeout(() => globalController.abort(), timeoutMs);
|
|
92143
|
+
const clientDisconnected = () => res.destroyed && !res.writableEnded;
|
|
92144
|
+
const abortError = () => clientDisconnected() ? new ClientDisconnectedError() : new Error(`Request timed out after ${timeoutMs}ms`);
|
|
92143
92145
|
const onClientClose = () => {
|
|
92144
|
-
if (!globalController.signal.aborted) {
|
|
92146
|
+
if (!res.writableEnded && !globalController.signal.aborted) {
|
|
92145
92147
|
console.log(`[ClawRouter] Client disconnected \u2014 aborting upstream request`);
|
|
92146
92148
|
globalController.abort();
|
|
92147
92149
|
}
|
|
92148
92150
|
};
|
|
92149
|
-
|
|
92151
|
+
res.on("close", onClientClose);
|
|
92152
|
+
if (res.destroyed) onClientClose();
|
|
92150
92153
|
try {
|
|
92151
92154
|
let modelsToTry;
|
|
92152
92155
|
const excludeList = options.excludeModels ?? loadExcludeList();
|
|
@@ -92205,7 +92208,7 @@ data: [DONE]
|
|
|
92205
92208
|
completed = true;
|
|
92206
92209
|
deduplicator.removeInflight(dedupKey);
|
|
92207
92210
|
clearTimeout(timeoutId);
|
|
92208
|
-
|
|
92211
|
+
res.removeListener("close", onClientClose);
|
|
92209
92212
|
return;
|
|
92210
92213
|
}
|
|
92211
92214
|
const contextExcluded = fullChain.filter((m) => !contextFiltered.includes(m));
|
|
@@ -92304,7 +92307,7 @@ data: [DONE]
|
|
|
92304
92307
|
}
|
|
92305
92308
|
deduplicator.removeInflight(dedupKey);
|
|
92306
92309
|
clearTimeout(timeoutId);
|
|
92307
|
-
|
|
92310
|
+
res.removeListener("close", onClientClose);
|
|
92308
92311
|
return;
|
|
92309
92312
|
}
|
|
92310
92313
|
if (excluded.length > 0) {
|
|
@@ -92335,7 +92338,7 @@ data: [DONE]
|
|
|
92335
92338
|
const tryModel = modelsToTry[i];
|
|
92336
92339
|
const isLastAttempt = i === modelsToTry.length - 1;
|
|
92337
92340
|
if (globalController.signal.aborted) {
|
|
92338
|
-
throw
|
|
92341
|
+
throw abortError();
|
|
92339
92342
|
}
|
|
92340
92343
|
console.log(`[ClawRouter] Trying model ${i + 1}/${modelsToTry.length}: ${tryModel}`);
|
|
92341
92344
|
const perAttemptTimeoutMs = timeoutForModel(tryModel);
|
|
@@ -92355,7 +92358,7 @@ data: [DONE]
|
|
|
92355
92358
|
);
|
|
92356
92359
|
clearTimeout(modelTimeoutId);
|
|
92357
92360
|
if (globalController.signal.aborted) {
|
|
92358
|
-
throw
|
|
92361
|
+
throw abortError();
|
|
92359
92362
|
}
|
|
92360
92363
|
if (!result.success && modelController.signal.aborted && !isLastAttempt) {
|
|
92361
92364
|
console.log(
|
|
@@ -92567,7 +92570,7 @@ data: [DONE]
|
|
|
92567
92570
|
break;
|
|
92568
92571
|
}
|
|
92569
92572
|
clearTimeout(timeoutId);
|
|
92570
|
-
|
|
92573
|
+
res.removeListener("close", onClientClose);
|
|
92571
92574
|
if (heartbeatInterval) {
|
|
92572
92575
|
clearInterval(heartbeatInterval);
|
|
92573
92576
|
heartbeatInterval = void 0;
|
|
@@ -93070,12 +93073,16 @@ data: [DONE]
|
|
|
93070
93073
|
completed = true;
|
|
93071
93074
|
} catch (err) {
|
|
93072
93075
|
clearTimeout(timeoutId);
|
|
93073
|
-
|
|
93076
|
+
res.removeListener("close", onClientClose);
|
|
93074
93077
|
if (heartbeatInterval) {
|
|
93075
93078
|
clearInterval(heartbeatInterval);
|
|
93076
93079
|
heartbeatInterval = void 0;
|
|
93077
93080
|
}
|
|
93078
93081
|
deduplicator.removeInflight(dedupKey);
|
|
93082
|
+
if (err instanceof ClientDisconnectedError || err instanceof Error && err.name === "AbortError" && clientDisconnected()) {
|
|
93083
|
+
console.log(`[ClawRouter] Request cancelled \u2014 client disconnected`);
|
|
93084
|
+
return;
|
|
93085
|
+
}
|
|
93079
93086
|
balanceMonitor.invalidate();
|
|
93080
93087
|
if (err instanceof Error && err.name === "AbortError") {
|
|
93081
93088
|
throw new Error(`Request timed out after ${timeoutMs}ms`, { cause: err });
|
|
@@ -93131,7 +93138,7 @@ data: [DONE]
|
|
|
93131
93138
|
});
|
|
93132
93139
|
}
|
|
93133
93140
|
}
|
|
93134
|
-
var paymentStore, BLOCKRUN_API, BLOCKRUN_SOLANA_API, IMAGE_DIR, AUDIO_DIR, VIDEO_DIR, AUTO_MODEL, ROUTING_PROFILES, FREE_MODELS, FREE_MODEL, MAX_MESSAGES, CONTEXT_LIMIT_KB, HEARTBEAT_INTERVAL_MS, BALANCE_CHECK_TIMEOUT_MS, DEFAULT_REQUEST_TIMEOUT_MS, PER_MODEL_TIMEOUT_MS, REASONING_MODEL_TIMEOUT_MS, REASONING_MODEL_IDS, MAX_FALLBACK_ATTEMPTS, HEALTH_CHECK_TIMEOUT_MS, RATE_LIMIT_COOLDOWN_MS, OVERLOAD_COOLDOWN_MS, PORT_RETRY_ATTEMPTS, PORT_RETRY_DELAY_MS, MODEL_BODY_READ_TIMEOUT_MS, ERROR_BODY_READ_TIMEOUT_MS, rateLimitedModels, overloadedModels, perProviderErrors, BALANCE_CHECK_BUFFER, BALANCE_PREFLIGHT_OUTPUT_TOKEN_CAP, PROVIDER_ERROR_PATTERNS, DEGRADED_RESPONSE_PATTERNS, DEGRADED_LOOP_PATTERNS, VALID_ROLES, ROLE_MAPPINGS, VALID_TOOL_ID_PATTERN, KIMI_BLOCK_RE, KIMI_TOKEN_RE, THINKING_TAG_RE, THINKING_BLOCK_RE, BLOCKRUN_MODEL_BY_ID, IMAGE_PRICING, IMAGE_MODEL_IDS, IMAGE_MODEL_SIZES, IMAGE_MODEL_ALIASES, VIDEO_PRICING, PHONE_PRICING;
|
|
93141
|
+
var paymentStore, BLOCKRUN_API, BLOCKRUN_SOLANA_API, IMAGE_DIR, AUDIO_DIR, VIDEO_DIR, AUTO_MODEL, ROUTING_PROFILES, FREE_MODELS, FREE_MODEL, MAX_MESSAGES, CONTEXT_LIMIT_KB, HEARTBEAT_INTERVAL_MS, BALANCE_CHECK_TIMEOUT_MS, DEFAULT_REQUEST_TIMEOUT_MS, PER_MODEL_TIMEOUT_MS, REASONING_MODEL_TIMEOUT_MS, REASONING_MODEL_IDS, MAX_FALLBACK_ATTEMPTS, HEALTH_CHECK_TIMEOUT_MS, RATE_LIMIT_COOLDOWN_MS, OVERLOAD_COOLDOWN_MS, PORT_RETRY_ATTEMPTS, PORT_RETRY_DELAY_MS, MODEL_BODY_READ_TIMEOUT_MS, ERROR_BODY_READ_TIMEOUT_MS, ClientDisconnectedError, rateLimitedModels, overloadedModels, perProviderErrors, BALANCE_CHECK_BUFFER, BALANCE_PREFLIGHT_OUTPUT_TOKEN_CAP, PROVIDER_ERROR_PATTERNS, DEGRADED_RESPONSE_PATTERNS, DEGRADED_LOOP_PATTERNS, VALID_ROLES, ROLE_MAPPINGS, VALID_TOOL_ID_PATTERN, KIMI_BLOCK_RE, KIMI_TOKEN_RE, THINKING_TAG_RE, THINKING_BLOCK_RE, BLOCKRUN_MODEL_BY_ID, IMAGE_PRICING, IMAGE_MODEL_IDS, IMAGE_MODEL_SIZES, IMAGE_MODEL_ALIASES, VIDEO_PRICING, PHONE_PRICING;
|
|
93135
93142
|
var init_proxy = __esm({
|
|
93136
93143
|
"src/proxy.ts"() {
|
|
93137
93144
|
"use strict";
|
|
@@ -93211,6 +93218,12 @@ var init_proxy = __esm({
|
|
|
93211
93218
|
PORT_RETRY_DELAY_MS = 1e3;
|
|
93212
93219
|
MODEL_BODY_READ_TIMEOUT_MS = 3e5;
|
|
93213
93220
|
ERROR_BODY_READ_TIMEOUT_MS = 3e4;
|
|
93221
|
+
ClientDisconnectedError = class extends Error {
|
|
93222
|
+
constructor() {
|
|
93223
|
+
super("Client disconnected");
|
|
93224
|
+
this.name = "ClientDisconnectedError";
|
|
93225
|
+
}
|
|
93226
|
+
};
|
|
93214
93227
|
rateLimitedModels = /* @__PURE__ */ new Map();
|
|
93215
93228
|
overloadedModels = /* @__PURE__ */ new Map();
|
|
93216
93229
|
perProviderErrors = /* @__PURE__ */ new Map();
|
package/package.json
CHANGED