@hybridaione/hybridclaw 0.2.7 → 0.2.10
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/CHANGELOG.md +63 -1
- package/README.md +5 -9
- package/config.example.json +2 -0
- package/container/package-lock.json +2 -2
- package/container/package.json +11 -2
- package/container/src/index.ts +22 -21
- package/container/src/model-retry.ts +19 -0
- package/container/src/tools.ts +445 -38
- package/container/src/types.ts +1 -0
- package/dist/channels/discord/prompt-adapter.d.ts +3 -0
- package/dist/channels/discord/prompt-adapter.d.ts.map +1 -0
- package/dist/channels/discord/prompt-adapter.js +26 -0
- package/dist/channels/discord/prompt-adapter.js.map +1 -0
- package/dist/channels/discord/runtime.d.ts.map +1 -1
- package/dist/channels/discord/runtime.js +41 -6
- package/dist/channels/discord/runtime.js.map +1 -1
- package/dist/channels/discord/send-permissions.d.ts +19 -0
- package/dist/channels/discord/send-permissions.d.ts.map +1 -0
- package/dist/channels/discord/send-permissions.js +112 -0
- package/dist/channels/discord/send-permissions.js.map +1 -0
- package/dist/channels/discord/tool-actions.d.ts +13 -1
- package/dist/channels/discord/tool-actions.d.ts.map +1 -1
- package/dist/channels/discord/tool-actions.js +778 -17
- package/dist/channels/discord/tool-actions.js.map +1 -1
- package/dist/channels/prompt-adapters.d.ts +14 -0
- package/dist/channels/prompt-adapters.d.ts.map +1 -0
- package/dist/channels/prompt-adapters.js +37 -0
- package/dist/channels/prompt-adapters.js.map +1 -0
- package/dist/config.d.ts +2 -0
- package/dist/config.d.ts.map +1 -1
- package/dist/config.js +4 -0
- package/dist/config.js.map +1 -1
- package/dist/container-runner.d.ts.map +1 -1
- package/dist/container-runner.js +31 -7
- package/dist/container-runner.js.map +1 -1
- package/dist/gateway-service.d.ts.map +1 -1
- package/dist/gateway-service.js +12 -3
- package/dist/gateway-service.js.map +1 -1
- package/dist/gateway.js +43 -8
- package/dist/gateway.js.map +1 -1
- package/dist/health.d.ts.map +1 -1
- package/dist/health.js +69 -12
- package/dist/health.js.map +1 -1
- package/dist/hybridai-models.d.ts.map +1 -1
- package/dist/hybridai-models.js +42 -4
- package/dist/hybridai-models.js.map +1 -1
- package/dist/prompt-hooks.d.ts +3 -0
- package/dist/prompt-hooks.d.ts.map +1 -1
- package/dist/prompt-hooks.js +40 -4
- package/dist/prompt-hooks.js.map +1 -1
- package/dist/runtime-config.d.ts +8 -0
- package/dist/runtime-config.d.ts.map +1 -1
- package/dist/runtime-config.js +35 -1
- package/dist/runtime-config.js.map +1 -1
- package/dist/silent-reply-stream.d.ts +6 -0
- package/dist/silent-reply-stream.d.ts.map +1 -0
- package/dist/silent-reply-stream.js +51 -0
- package/dist/silent-reply-stream.js.map +1 -0
- package/dist/silent-reply.d.ts +5 -0
- package/dist/silent-reply.d.ts.map +1 -0
- package/dist/silent-reply.js +31 -0
- package/dist/silent-reply.js.map +1 -0
- package/dist/types.d.ts +1 -0
- package/dist/types.d.ts.map +1 -1
- package/dist/types.js.map +1 -1
- package/docs/index.html +10 -10
- package/package.json +26 -3
- package/.github/workflows/ci.yml +0 -70
- package/.github/workflows/pages.yml +0 -41
- package/.husky/pre-commit +0 -1
- package/CONTRIBUTING.md +0 -33
- package/biome.json +0 -35
- package/dist/colors.d.ts +0 -18
- package/dist/colors.d.ts.map +0 -1
- package/dist/colors.js +0 -27
- package/dist/colors.js.map +0 -1
- package/dist/discord-stream.d.ts +0 -32
- package/dist/discord-stream.d.ts.map +0 -1
- package/dist/discord-stream.js +0 -196
- package/dist/discord-stream.js.map +0 -1
- package/dist/discord.basic.test.d.ts +0 -2
- package/dist/discord.basic.test.d.ts.map +0 -1
- package/dist/discord.basic.test.js +0 -38
- package/dist/discord.basic.test.js.map +0 -1
- package/dist/discord.d.ts +0 -6
- package/dist/discord.d.ts.map +0 -1
- package/dist/discord.js +0 -4
- package/dist/discord.js.map +0 -1
- package/dist/gateway-service.media-routing.test.d.ts +0 -2
- package/dist/gateway-service.media-routing.test.d.ts.map +0 -1
- package/dist/gateway-service.media-routing.test.js +0 -29
- package/dist/gateway-service.media-routing.test.js.map +0 -1
- package/dist/git-commit.d.ts +0 -2
- package/dist/git-commit.d.ts.map +0 -1
- package/dist/git-commit.js +0 -63
- package/dist/git-commit.js.map +0 -1
- package/dist/hatch.d.ts +0 -7
- package/dist/hatch.d.ts.map +0 -1
- package/dist/hatch.js +0 -99
- package/dist/hatch.js.map +0 -1
- package/dist/index.d.ts +0 -2
- package/dist/index.d.ts.map +0 -1
- package/dist/index.js +0 -60
- package/dist/index.js.map +0 -1
- package/dist/token-efficiency.basic.test.d.ts +0 -2
- package/dist/token-efficiency.basic.test.d.ts.map +0 -1
- package/dist/token-efficiency.basic.test.js +0 -29
- package/dist/token-efficiency.basic.test.js.map +0 -1
- package/src/agent.ts +0 -86
- package/src/audit-cli.ts +0 -327
- package/src/audit-events.ts +0 -201
- package/src/audit-trail.ts +0 -428
- package/src/channels/discord/attachments.ts +0 -336
- package/src/channels/discord/debounce.ts +0 -25
- package/src/channels/discord/delivery.ts +0 -150
- package/src/channels/discord/human-delay.ts +0 -48
- package/src/channels/discord/inbound.ts +0 -260
- package/src/channels/discord/mentions.ts +0 -154
- package/src/channels/discord/presence.ts +0 -148
- package/src/channels/discord/rate-limiter.ts +0 -58
- package/src/channels/discord/reactions.ts +0 -211
- package/src/channels/discord/runtime.ts +0 -2216
- package/src/channels/discord/stream.ts +0 -294
- package/src/channels/discord/tool-actions.ts +0 -373
- package/src/channels/discord/typing.ts +0 -140
- package/src/chunk.ts +0 -161
- package/src/cli.ts +0 -911
- package/src/config.ts +0 -403
- package/src/container-runner.ts +0 -522
- package/src/container-setup.ts +0 -317
- package/src/conversation.ts +0 -82
- package/src/db.ts +0 -2718
- package/src/delegation-manager.ts +0 -49
- package/src/env.ts +0 -36
- package/src/gateway-client.ts +0 -241
- package/src/gateway-service.ts +0 -2708
- package/src/gateway-types.ts +0 -137
- package/src/gateway.ts +0 -827
- package/src/health.ts +0 -357
- package/src/heartbeat.ts +0 -419
- package/src/hybridai-bots.ts +0 -57
- package/src/hybridai-models.ts +0 -158
- package/src/instruction-approval-audit.ts +0 -90
- package/src/instruction-integrity.ts +0 -197
- package/src/ipc.ts +0 -181
- package/src/logger.ts +0 -29
- package/src/memory-consolidation.ts +0 -41
- package/src/memory-service.ts +0 -606
- package/src/mount-security.ts +0 -261
- package/src/observability-ingest.ts +0 -888
- package/src/onboarding.ts +0 -719
- package/src/proactive-policy.ts +0 -46
- package/src/prompt-hooks.ts +0 -326
- package/src/runtime-config.ts +0 -1808
- package/src/scheduled-task-runner.ts +0 -256
- package/src/scheduler.ts +0 -819
- package/src/session-export.ts +0 -196
- package/src/session-maintenance.ts +0 -367
- package/src/session-transcripts.ts +0 -54
- package/src/side-effects.ts +0 -97
- package/src/skills-guard.ts +0 -1584
- package/src/skills.ts +0 -1036
- package/src/token-efficiency.ts +0 -266
- package/src/tui.ts +0 -604
- package/src/types.ts +0 -428
- package/src/update.ts +0 -445
- package/src/workspace.ts +0 -223
- package/tests/approval-policy.test.ts +0 -335
- package/tests/discord.basic.test.ts +0 -304
- package/tests/discord.human-presence.test.ts +0 -85
- package/tests/gateway-service.media-routing.test.ts +0 -39
- package/tests/hybridai-client.test.ts +0 -112
- package/tests/hybridai-models.test.ts +0 -46
- package/tests/memory-service.test.ts +0 -1114
- package/tests/token-efficiency.basic.test.ts +0 -38
- package/tests/token-usage.cache.test.ts +0 -128
- package/tsconfig.json +0 -18
- package/vitest.e2e.config.ts +0 -17
- package/vitest.integration.config.ts +0 -17
- package/vitest.live.config.ts +0 -18
- package/vitest.unit.config.ts +0 -24
package/CHANGELOG.md
CHANGED
|
@@ -2,7 +2,69 @@
|
|
|
2
2
|
|
|
3
3
|
## [Unreleased]
|
|
4
4
|
|
|
5
|
-
|
|
5
|
+
### Added
|
|
6
|
+
|
|
7
|
+
### Changed
|
|
8
|
+
|
|
9
|
+
### Fixed
|
|
10
|
+
|
|
11
|
+
## [0.2.10](https://github.com/HybridAIOne/hybridclaw/tree/v0.2.10)
|
|
12
|
+
|
|
13
|
+
### Added
|
|
14
|
+
|
|
15
|
+
- **Model retry policy helpers + tests**: Added shared model stream-fallback/retry predicates with dedicated unit coverage for retryable/non-retryable HybridAI error classes.
|
|
16
|
+
- **Message tool schema regression test**: Added explicit schema test coverage to enforce valid `components` parameter structure for the `message` tool definition.
|
|
17
|
+
|
|
18
|
+
### Changed
|
|
19
|
+
|
|
20
|
+
- **Stream failure fallback behavior**: Container model-call flow now applies stream-to-non-stream fallback policy through centralized retry helpers for consistent error classification.
|
|
21
|
+
|
|
22
|
+
### Fixed
|
|
23
|
+
|
|
24
|
+
- **HybridAI function schema rejection**: Fixed `message` tool `components` schema by defining `items` for the array variant, resolving `invalid_function_parameters` 400 failures.
|
|
25
|
+
- **HybridAI 500 handling robustness**: Streamed 5xx API failures now trigger the non-stream fallback path before hard-failing the turn.
|
|
26
|
+
|
|
27
|
+
## [0.2.9](https://github.com/HybridAIOne/hybridclaw/tree/v0.2.9)
|
|
28
|
+
|
|
29
|
+
### Added
|
|
30
|
+
|
|
31
|
+
- **Release bundle guard scripts**: Added root and container `release:check` scripts that validate `npm pack --dry-run` contents and fail on forbidden files (tests, source, CI/config artifacts).
|
|
32
|
+
- **Dry-run publish helpers**: Added `publish:dry` scripts for root and container package smoke checks before publish.
|
|
33
|
+
|
|
34
|
+
### Changed
|
|
35
|
+
|
|
36
|
+
- **NPM package allowlists**: Added explicit `files` allowlists for root and container packages so publish output is limited to runtime assets and docs/templates/skills that HybridClaw loads at runtime.
|
|
37
|
+
- **Prepack gating**: Root and container packages now run clean build + release bundle validation during `prepack`.
|
|
38
|
+
- **CI packaging checks**: CI now runs root/container release bundle checks to catch publish-regression changes on PRs and pushes.
|
|
39
|
+
- **Silent reply token handling**: Centralized `__MESSAGE_SEND_HANDLED__` parsing/cleanup, added streaming prefix buffering for Discord/API output paths, and aligned prompt token constants with shared silent-reply utilities.
|
|
40
|
+
- **CLI build output mode**: Root `build` script now enforces executable mode on `dist/cli.js` after TypeScript compilation.
|
|
41
|
+
|
|
42
|
+
### Fixed
|
|
43
|
+
|
|
44
|
+
- **Silent token leakage in streams/history**: Streaming token fragments are now suppressed until divergence/confirmation, trailing silent tokens are stripped from mixed replies, and silent assistant placeholders are filtered from conversation history before model calls.
|
|
45
|
+
|
|
46
|
+
## [0.2.8](https://github.com/HybridAIOne/hybridclaw/tree/v0.2.8)
|
|
47
|
+
|
|
48
|
+
### Added
|
|
49
|
+
|
|
50
|
+
- **Discord send policy controls**: Added runtime config for `discord.sendPolicy` (`open|allowlist|disabled`) with global/channel/guild/user/role allowlist checks for outbound sends.
|
|
51
|
+
- **Channel-aware prompt adapters**: Added channel-specific message-tool hint adapters (including Discord action/component guidance) injected into system prompts.
|
|
52
|
+
- **Expanded Discord message actions**: Added `react`, `quote-reply`, `edit`, `delete`, `pin`, `unpin`, `thread-create`, and `thread-reply` actions to the `message` tool path.
|
|
53
|
+
- **Message-tool regression coverage**: Added focused unit coverage for action aliases, target normalization, member/channel lookup behavior, send-policy checks, and channel hint injection.
|
|
54
|
+
|
|
55
|
+
### Changed
|
|
56
|
+
|
|
57
|
+
- **Message-tool intent guidance**: System prompt guidance now includes explicit send/post/DM/notify triggers, send parameter guidance (`to` + message), and reply suppression token handling for tool-only sends.
|
|
58
|
+
- **Action alias + target normalization**: Message action normalization now supports natural aliases (`dm`, `post`, `reply`, `respond`, `history`, `fetch`, `lookup`, `whois`) and normalizes Discord prefixes/mentions.
|
|
59
|
+
- **Tool description enrichment**: `message` tool descriptions now emphasize natural-language intent phrases and enumerate current/other configured Discord channels with supported actions.
|
|
60
|
+
- **Single-call DM targeting**: `send` now resolves user targets inline (IDs, mentions, usernames/display names with guild context), including fallback via `user`/`username` when no explicit channel target is passed.
|
|
61
|
+
- **Discord action API flexibility**: `/api/discord/action` now accepts normalized aliases and extended send payload fields (`components`, `contextChannelId`, threading/message mutation fields).
|
|
62
|
+
|
|
63
|
+
### Fixed
|
|
64
|
+
|
|
65
|
+
- **Structured target-resolution errors**: Member/user lookup failures now return structured JSON errors with disambiguation candidates and actionable hints.
|
|
66
|
+
- **Ambiguous target handling**: Added `resolveAmbiguous` support (`error|best`) to allow safe candidate return or best-match auto-resolution for member/user lookups.
|
|
67
|
+
- **Duplicate send-reply leakage**: Gateway chat responses now strip the message-send silent reply token and normalize final user-visible success text.
|
|
6
68
|
|
|
7
69
|
## [0.2.7](https://github.com/HybridAIOne/hybridclaw/tree/v0.2.7)
|
|
8
70
|
|
package/README.md
CHANGED
|
@@ -11,17 +11,13 @@ npm install -g @hybridaione/hybridclaw
|
|
|
11
11
|
hybridclaw onboarding
|
|
12
12
|
```
|
|
13
13
|
|
|
14
|
-
Latest release: [v0.2.
|
|
14
|
+
Latest release: [v0.2.10](https://github.com/HybridAIOne/hybridclaw/releases/tag/v0.2.10)
|
|
15
15
|
|
|
16
|
-
## Release highlights (v0.2.
|
|
16
|
+
## Release highlights (v0.2.10)
|
|
17
17
|
|
|
18
|
-
-
|
|
19
|
-
-
|
|
20
|
-
-
|
|
21
|
-
- `browser_upload` now supports selector targets and automatic fallback from wrapper refs to detected `input[type="file"]` elements.
|
|
22
|
-
- HybridAI status/usage context metrics now use a curated static context-window catalog (Claude/Gemini/GPT-5) with family-aware fallback matching, and runtime supports `hybridai.maxTokens` for default completion budgeting.
|
|
23
|
-
- Model-usage telemetry now captures cache read/write token counters where providers expose them, and prompt-dump diagnostics include media plus allowed/blocked tool context.
|
|
24
|
-
- CLI container readiness checks now resolve the package install root to avoid non-root invocation failures.
|
|
18
|
+
- Fixed HybridAI `400 invalid_function_parameters` failures by correcting `message.components` schema (`array` now defines `items`).
|
|
19
|
+
- Improved HybridAI reliability by centralizing stream-fallback/retry error classification in the container runtime.
|
|
20
|
+
- Added regression tests for message-tool schema validity and HybridAI retry/fallback behavior.
|
|
25
21
|
|
|
26
22
|
## HybridAI Advantage
|
|
27
23
|
|
package/config.example.json
CHANGED
|
@@ -1,12 +1,12 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "hybridclaw-agent",
|
|
3
|
-
"version": "0.2.
|
|
3
|
+
"version": "0.2.10",
|
|
4
4
|
"lockfileVersion": 3,
|
|
5
5
|
"requires": true,
|
|
6
6
|
"packages": {
|
|
7
7
|
"": {
|
|
8
8
|
"name": "hybridclaw-agent",
|
|
9
|
-
"version": "0.2.
|
|
9
|
+
"version": "0.2.10",
|
|
10
10
|
"dependencies": {
|
|
11
11
|
"@mozilla/readability": "^0.6.0",
|
|
12
12
|
"agent-browser": "^0.15.1",
|
package/container/package.json
CHANGED
|
@@ -1,10 +1,19 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "hybridclaw-agent",
|
|
3
|
-
"version": "0.2.
|
|
3
|
+
"version": "0.2.10",
|
|
4
4
|
"type": "module",
|
|
5
|
+
"main": "dist/index.js",
|
|
6
|
+
"files": [
|
|
7
|
+
"dist/",
|
|
8
|
+
"Dockerfile"
|
|
9
|
+
],
|
|
5
10
|
"scripts": {
|
|
11
|
+
"clean": "node -e \"const fs=require('node:fs');fs.rmSync('dist',{recursive:true,force:true});\"",
|
|
6
12
|
"build": "tsc",
|
|
7
|
-
"lint": "tsc --noEmit --noUnusedLocals --noUnusedParameters"
|
|
13
|
+
"lint": "tsc --noEmit --noUnusedLocals --noUnusedParameters",
|
|
14
|
+
"prepack": "npm run clean && npm run build && npm run release:check",
|
|
15
|
+
"release:check": "node ./scripts/release-check.mjs",
|
|
16
|
+
"publish:dry": "npm publish --dry-run"
|
|
8
17
|
},
|
|
9
18
|
"dependencies": {
|
|
10
19
|
"@mozilla/readability": "^0.6.0",
|
package/container/src/index.ts
CHANGED
|
@@ -8,12 +8,12 @@ import {
|
|
|
8
8
|
runAfterToolHooks,
|
|
9
9
|
runBeforeToolHooks,
|
|
10
10
|
} from './extensions.js';
|
|
11
|
-
import {
|
|
12
|
-
callHybridAI,
|
|
13
|
-
callHybridAIStream,
|
|
14
|
-
HybridAIRequestError,
|
|
15
|
-
} from './hybridai-client.js';
|
|
11
|
+
import { callHybridAI, callHybridAIStream } from './hybridai-client.js';
|
|
16
12
|
import { waitForInput, writeOutput } from './ipc.js';
|
|
13
|
+
import {
|
|
14
|
+
isRetryableModelError,
|
|
15
|
+
shouldFallbackFromStreamError,
|
|
16
|
+
} from './model-retry.js';
|
|
17
17
|
import {
|
|
18
18
|
accumulateApiUsage,
|
|
19
19
|
createTokenUsageStats,
|
|
@@ -23,6 +23,7 @@ import {
|
|
|
23
23
|
} from './token-usage.js';
|
|
24
24
|
import {
|
|
25
25
|
executeTool,
|
|
26
|
+
getMessageToolDescription,
|
|
26
27
|
getPendingSideEffects,
|
|
27
28
|
resetSideEffects,
|
|
28
29
|
setGatewayContext,
|
|
@@ -304,16 +305,6 @@ function emitStreamDelta(delta: string): void {
|
|
|
304
305
|
console.error(`[stream] ${payload}`);
|
|
305
306
|
}
|
|
306
307
|
|
|
307
|
-
function isRetryableError(err: unknown): boolean {
|
|
308
|
-
if (err instanceof HybridAIRequestError) {
|
|
309
|
-
return err.status === 429 || (err.status >= 500 && err.status <= 504);
|
|
310
|
-
}
|
|
311
|
-
const message = err instanceof Error ? err.message : String(err);
|
|
312
|
-
return /fetch failed|network|socket|timeout|timed out|ECONNRESET|ECONNREFUSED|EAI_AGAIN/i.test(
|
|
313
|
-
message,
|
|
314
|
-
);
|
|
315
|
-
}
|
|
316
|
-
|
|
317
308
|
function inferToolError(result: string, blockedReason: string | null): boolean {
|
|
318
309
|
if (blockedReason) return true;
|
|
319
310
|
return /\b(error|failed|denied|forbidden|timed out|timeout|exception|invalid)\b/i.test(
|
|
@@ -537,11 +528,7 @@ async function callHybridAIWithRetry(params: {
|
|
|
537
528
|
maxTokens,
|
|
538
529
|
);
|
|
539
530
|
} catch (streamErr) {
|
|
540
|
-
const fallbackEligible =
|
|
541
|
-
streamErr instanceof HybridAIRequestError &&
|
|
542
|
-
streamErr.status >= 400 &&
|
|
543
|
-
streamErr.status < 500 &&
|
|
544
|
-
streamErr.status !== 429;
|
|
531
|
+
const fallbackEligible = shouldFallbackFromStreamError(streamErr);
|
|
545
532
|
if (!fallbackEligible) throw streamErr;
|
|
546
533
|
response = await callHybridAI(
|
|
547
534
|
baseUrl,
|
|
@@ -574,7 +561,9 @@ async function callHybridAIWithRetry(params: {
|
|
|
574
561
|
return response;
|
|
575
562
|
} catch (err) {
|
|
576
563
|
const retryable =
|
|
577
|
-
RETRY_ENABLED &&
|
|
564
|
+
RETRY_ENABLED &&
|
|
565
|
+
isRetryableModelError(err) &&
|
|
566
|
+
attempt < RETRY_MAX_ATTEMPTS;
|
|
578
567
|
await emitRuntimeEvent({
|
|
579
568
|
event: retryable ? 'model_retry' : 'model_error',
|
|
580
569
|
attempt,
|
|
@@ -940,6 +929,16 @@ function resolveTools(input: ContainerInput): ToolDefinition[] {
|
|
|
940
929
|
);
|
|
941
930
|
tools = tools.filter((tool) => !blocked.has(tool.function.name));
|
|
942
931
|
}
|
|
932
|
+
tools = tools.map((tool) => {
|
|
933
|
+
if (tool.function.name !== 'message') return tool;
|
|
934
|
+
return {
|
|
935
|
+
...tool,
|
|
936
|
+
function: {
|
|
937
|
+
...tool.function,
|
|
938
|
+
description: getMessageToolDescription(input.channelId),
|
|
939
|
+
},
|
|
940
|
+
};
|
|
941
|
+
});
|
|
943
942
|
// Sort alphabetically for deterministic tool ordering (request/cache stability)
|
|
944
943
|
tools.sort((a, b) => a.function.name.localeCompare(b.function.name));
|
|
945
944
|
return tools;
|
|
@@ -979,6 +978,7 @@ async function main(): Promise<void> {
|
|
|
979
978
|
firstInput.gatewayBaseUrl,
|
|
980
979
|
firstInput.gatewayApiToken,
|
|
981
980
|
firstInput.channelId,
|
|
981
|
+
firstInput.configuredDiscordChannels,
|
|
982
982
|
);
|
|
983
983
|
setModelContext(
|
|
984
984
|
firstInput.baseUrl,
|
|
@@ -1074,6 +1074,7 @@ async function main(): Promise<void> {
|
|
|
1074
1074
|
input.gatewayBaseUrl,
|
|
1075
1075
|
input.gatewayApiToken,
|
|
1076
1076
|
input.channelId,
|
|
1077
|
+
input.configuredDiscordChannels,
|
|
1077
1078
|
);
|
|
1078
1079
|
setModelContext(input.baseUrl, apiKey, input.model, input.chatbotId);
|
|
1079
1080
|
setMediaContext(input.media);
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
import { HybridAIRequestError } from './hybridai-client.js';
|
|
2
|
+
|
|
3
|
+
const TRANSIENT_NETWORK_ERROR_RE =
|
|
4
|
+
/fetch failed|network|socket|timeout|timed out|ECONNRESET|ECONNREFUSED|EAI_AGAIN/i;
|
|
5
|
+
|
|
6
|
+
export function shouldFallbackFromStreamError(error: unknown): boolean {
|
|
7
|
+
if (!(error instanceof HybridAIRequestError)) return false;
|
|
8
|
+
// Keep 429 on retry/backoff path; fallback does not help throttling.
|
|
9
|
+
if (error.status === 429) return false;
|
|
10
|
+
return error.status >= 400 && error.status <= 599;
|
|
11
|
+
}
|
|
12
|
+
|
|
13
|
+
export function isRetryableModelError(error: unknown): boolean {
|
|
14
|
+
if (error instanceof HybridAIRequestError) {
|
|
15
|
+
return error.status === 429 || (error.status >= 500 && error.status <= 504);
|
|
16
|
+
}
|
|
17
|
+
const message = error instanceof Error ? error.message : String(error);
|
|
18
|
+
return TRANSIENT_NETWORK_ERROR_RE.test(message);
|
|
19
|
+
}
|