@stackbilt/llm-providers 1.2.0 → 1.5.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 (95) hide show
  1. package/LICENSE +0 -0
  2. package/README.md +58 -11
  3. package/dist/errors.d.ts +14 -0
  4. package/dist/errors.d.ts.map +1 -1
  5. package/dist/errors.js +19 -0
  6. package/dist/errors.js.map +1 -1
  7. package/dist/factory.d.ts +8 -4
  8. package/dist/factory.d.ts.map +1 -1
  9. package/dist/factory.js +129 -47
  10. package/dist/factory.js.map +1 -1
  11. package/dist/image/index.d.ts +0 -0
  12. package/dist/image/index.d.ts.map +0 -0
  13. package/dist/image/index.js +0 -0
  14. package/dist/image/index.js.map +0 -0
  15. package/dist/image/provider.d.ts +0 -0
  16. package/dist/image/provider.d.ts.map +0 -0
  17. package/dist/image/provider.js +0 -0
  18. package/dist/image/provider.js.map +0 -0
  19. package/dist/image/types.d.ts +0 -0
  20. package/dist/image/types.d.ts.map +0 -0
  21. package/dist/image/types.js +0 -0
  22. package/dist/image/types.js.map +0 -0
  23. package/dist/index.d.ts +10 -16
  24. package/dist/index.d.ts.map +1 -1
  25. package/dist/index.js +21 -85
  26. package/dist/index.js.map +1 -1
  27. package/dist/model-catalog.d.ts +42 -0
  28. package/dist/model-catalog.d.ts.map +1 -0
  29. package/dist/model-catalog.js +532 -0
  30. package/dist/model-catalog.js.map +1 -0
  31. package/dist/providers/anthropic.d.ts +1 -0
  32. package/dist/providers/anthropic.d.ts.map +1 -1
  33. package/dist/providers/anthropic.js +47 -14
  34. package/dist/providers/anthropic.js.map +1 -1
  35. package/dist/providers/base.d.ts +0 -0
  36. package/dist/providers/base.d.ts.map +0 -0
  37. package/dist/providers/base.js +0 -0
  38. package/dist/providers/base.js.map +0 -0
  39. package/dist/providers/cerebras.d.ts +1 -0
  40. package/dist/providers/cerebras.d.ts.map +1 -1
  41. package/dist/providers/cerebras.js +54 -7
  42. package/dist/providers/cerebras.js.map +1 -1
  43. package/dist/providers/cloudflare.d.ts +3 -0
  44. package/dist/providers/cloudflare.d.ts.map +1 -1
  45. package/dist/providers/cloudflare.js +81 -18
  46. package/dist/providers/cloudflare.js.map +1 -1
  47. package/dist/providers/groq.d.ts +1 -0
  48. package/dist/providers/groq.d.ts.map +1 -1
  49. package/dist/providers/groq.js +58 -7
  50. package/dist/providers/groq.js.map +1 -1
  51. package/dist/providers/openai.d.ts +1 -0
  52. package/dist/providers/openai.d.ts.map +1 -1
  53. package/dist/providers/openai.js +50 -17
  54. package/dist/providers/openai.js.map +1 -1
  55. package/dist/types.d.ts +0 -0
  56. package/dist/types.d.ts.map +0 -0
  57. package/dist/types.js +0 -0
  58. package/dist/types.js.map +0 -0
  59. package/dist/utils/circuit-breaker.d.ts +0 -0
  60. package/dist/utils/circuit-breaker.d.ts.map +0 -0
  61. package/dist/utils/circuit-breaker.js +0 -0
  62. package/dist/utils/circuit-breaker.js.map +0 -0
  63. package/dist/utils/cost-tracker.d.ts +0 -0
  64. package/dist/utils/cost-tracker.d.ts.map +0 -0
  65. package/dist/utils/cost-tracker.js +0 -0
  66. package/dist/utils/cost-tracker.js.map +0 -0
  67. package/dist/utils/credit-ledger.d.ts +0 -0
  68. package/dist/utils/credit-ledger.d.ts.map +0 -0
  69. package/dist/utils/credit-ledger.js +0 -0
  70. package/dist/utils/credit-ledger.js.map +0 -0
  71. package/dist/utils/exhaustion.d.ts +0 -0
  72. package/dist/utils/exhaustion.d.ts.map +0 -0
  73. package/dist/utils/exhaustion.js +0 -0
  74. package/dist/utils/exhaustion.js.map +0 -0
  75. package/dist/utils/hooks.d.ts +10 -0
  76. package/dist/utils/hooks.d.ts.map +1 -1
  77. package/dist/utils/hooks.js +1 -1
  78. package/dist/utils/hooks.js.map +1 -1
  79. package/dist/utils/latency-histogram.d.ts +0 -0
  80. package/dist/utils/latency-histogram.d.ts.map +0 -0
  81. package/dist/utils/latency-histogram.js +0 -0
  82. package/dist/utils/latency-histogram.js.map +0 -0
  83. package/dist/utils/logger.d.ts +0 -0
  84. package/dist/utils/logger.d.ts.map +0 -0
  85. package/dist/utils/logger.js +0 -0
  86. package/dist/utils/logger.js.map +0 -0
  87. package/dist/utils/retry.d.ts +0 -0
  88. package/dist/utils/retry.d.ts.map +0 -0
  89. package/dist/utils/retry.js +0 -0
  90. package/dist/utils/retry.js.map +0 -0
  91. package/dist/utils/schema-validator.d.ts +67 -0
  92. package/dist/utils/schema-validator.d.ts.map +1 -0
  93. package/dist/utils/schema-validator.js +140 -0
  94. package/dist/utils/schema-validator.js.map +1 -0
  95. package/package.json +1 -1
package/LICENSE CHANGED
File without changes
package/README.md CHANGED
@@ -8,6 +8,7 @@ A multi-provider LLM abstraction layer with automatic failover, graduated circui
8
8
  - **Graduated circuit breaker** -- 4-state machine (closed / degraded / recovering / open) with probabilistic traffic routing prevents cascading failures
9
9
  - **Exponential backoff retry** -- configurable delays, jitter, and per-error-class behavior
10
10
  - **Cost tracking and optimization** -- per-provider cost attribution, budget alerts with CreditLedger, automatic routing to cheaper providers
11
+ - **Declarative model catalog** -- semantic model metadata drives recommendations, provider defaults, and fallback routing
11
12
  - **Rate limit enforcement** -- CreditLedger tracks RPM/RPD/TPM/TPD per provider; factory skips providers that exceed limits
12
13
  - **Streaming** -- SSE streaming support for all providers
13
14
  - **Tool/function calling** -- OpenAI, Anthropic, Cerebras, and Cloudflare tool use with unified response format
@@ -66,11 +67,11 @@ const llm = LLMProviders.fromEnv(env, {
66
67
 
67
68
  | Provider | Models | Streaming | Tools | Notes |
68
69
  |----------|--------|-----------|-------|-------|
69
- | **OpenAI** | GPT-4o, GPT-4o Mini, GPT-4 Turbo, GPT-4 | Yes | Yes | Default: `gpt-4o-mini` |
70
- | **Anthropic** | Claude Opus 4.6, Sonnet 4.6, Sonnet 4, Haiku 4.5, 3.7 Sonnet, 3.5 Sonnet/Haiku, 3 Opus/Sonnet/Haiku | Yes | Yes | Default: `claude-haiku-4-5` |
71
- | **Cloudflare** | LLaMA 3.1 8B/70B, GPT-OSS 120B, Mistral 7B, Qwen 1.5, TinyLlama, and more | Yes | GPT-OSS only | Near-zero cost |
70
+ | **OpenAI** | GPT-4o Mini, GPT-4 Turbo, GPT-4, GPT-3.5 Turbo | Yes | Yes | Default: `gpt-4o-mini` |
71
+ | **Anthropic** | Claude Opus 4.6, Sonnet 4.6, Sonnet 4, Haiku 4.5, 3.7 Sonnet, 3.5 Sonnet/Haiku, 3 Opus/Sonnet | Yes | Yes | Default: `claude-haiku-4-5-20251001` |
72
+ | **Cloudflare** | Gemma 4 26B, Llama 4 Scout, GPT-OSS 120B, LLaMA 3.x, Mistral 7B, Qwen 1.5, TinyLlama, and more | Yes | GPT-OSS, Gemma 4, Llama 4 Scout | Default is request-aware and catalog-driven |
72
73
  | **Cerebras** | LLaMA 3.1 8B, LLaMA 3.3 70B, ZAI-GLM 4.7, Qwen 3 235B | Yes | GLM/Qwen only | ~2,200 tok/s |
73
- | **Groq** | LLaMA 3.3 70B Versatile, LLaMA 3.1 8B Instant | Yes | No | Ultra-fast inference |
74
+ | **Groq** | LLaMA 3.3 70B Versatile, LLaMA 3.1 8B Instant, GPT-OSS 120B | Yes | LLaMA 3.3 70B, GPT-OSS 120B | Ultra-fast inference |
74
75
 
75
76
  ### Provider Configuration
76
77
 
@@ -160,6 +161,49 @@ const llm = new LLMProviders({
160
161
  });
161
162
  ```
162
163
 
164
+ ## Model Catalog & Runtime Selection
165
+
166
+ Model selection is driven by a declarative catalog rather than a hardcoded fallback array. The selector intersects:
167
+
168
+ - requested use case and capabilities
169
+ - configured providers
170
+ - circuit breaker state (`CLOSED`, `DEGRADED`, `RECOVERING`, `OPEN`)
171
+ - CreditLedger utilization and projected burn/depletion pressure
172
+
173
+ The catalog also distinguishes active, compatibility, and retired models. Retired IDs can remain exported for compatibility, but they are not recommendation targets.
174
+
175
+ ```typescript
176
+ import {
177
+ MODEL_CATALOG,
178
+ MODEL_RECOMMENDATIONS,
179
+ getRecommendedModel,
180
+ inferUseCaseFromRequest
181
+ } from '@stackbilt/llm-providers';
182
+
183
+ const useCase = inferUseCaseFromRequest({
184
+ messages: [{ role: 'user', content: 'Call the weather tool' }],
185
+ tools: [{
186
+ type: 'function',
187
+ function: {
188
+ name: 'get_weather',
189
+ description: 'Get weather',
190
+ parameters: { type: 'object' }
191
+ }
192
+ }]
193
+ });
194
+
195
+ const model = getRecommendedModel('TOOL_CALLING', ['cloudflare', 'openai']);
196
+ ```
197
+
198
+ For runtime-aware recommendations from a configured instance:
199
+
200
+ ```typescript
201
+ const recommended = llm.getRecommendedModel({
202
+ messages: [{ role: 'user', content: 'Summarize this incident' }],
203
+ maxTokens: 800
204
+ });
205
+ ```
206
+
163
207
  ## Fallback Rules
164
208
 
165
209
  Customize when and how the factory falls back between providers:
@@ -178,7 +222,7 @@ const llm = new LLMProviders({
178
222
  });
179
223
  ```
180
224
 
181
- Default fallback priority includes all configured providers: Cloudflare → Cerebras → Groq → Anthropic → OpenAI.
225
+ Default provider precedence remains Cloudflare → Cerebras → Groq → Anthropic → OpenAI, but actual dispatch is catalog-driven and can be reordered at runtime by request fit, circuit-breaker state, and ledger burn-rate pressure.
182
226
 
183
227
  ## Error Handling
184
228
 
@@ -215,11 +259,11 @@ import { MODELS, getRecommendedModel } from '@stackbilt/llm-providers';
215
259
  MODELS.CLAUDE_OPUS_4_6; // 'claude-opus-4-6-20250618'
216
260
  MODELS.CLAUDE_SONNET_4_6; // 'claude-sonnet-4-6-20250618'
217
261
  MODELS.CLAUDE_HAIKU_4_5; // 'claude-haiku-4-5-20251001'
218
- MODELS.GPT_4O; // 'gpt-4o'
262
+ MODELS.GPT_4O; // 'gpt-4o' (deprecated / compatibility only)
219
263
  MODELS.GPT_4O_MINI; // 'gpt-4o-mini'
220
264
  MODELS.CEREBRAS_ZAI_GLM_4_7; // 'zai-glm-4.7'
221
265
 
222
- // Get best model for a use case given available providers
266
+ // Get best active model for a use case given available providers
223
267
  const model = getRecommendedModel('COST_EFFECTIVE', ['openai', 'cloudflare']);
224
268
  ```
225
269
 
@@ -230,12 +274,12 @@ const model = getRecommendedModel('COST_EFFECTIVE', ['openai', 'cloudflare']);
230
274
  | Class | Description |
231
275
  |-------|-------------|
232
276
  | `LLMProviders` | High-level facade -- initialize providers, generate responses, check health |
233
- | `LLMProviderFactory` | Lower-level factory with provider chain building and fallback logic |
277
+ | `LLMProviderFactory` | Lower-level factory with provider chain building, catalog-based routing, and fallback logic |
234
278
  | `OpenAIProvider` | OpenAI GPT models (streaming, tools) |
235
279
  | `AnthropicProvider` | Anthropic Claude models (streaming, tools) |
236
- | `CloudflareProvider` | Cloudflare Workers AI (streaming, tools on GPT-OSS, batch) |
280
+ | `CloudflareProvider` | Cloudflare Workers AI (streaming, tools on GPT-OSS/Gemma 4/Llama 4, batch) |
237
281
  | `CerebrasProvider` | Cerebras fast inference (streaming, tools on GLM/Qwen) |
238
- | `GroqProvider` | Groq fast inference (streaming) |
282
+ | `GroqProvider` | Groq fast inference (streaming, tools on GPT-OSS/LLaMA 3.3 70B) |
239
283
  | `BaseProvider` | Abstract base with shared resiliency, metrics, and cost calculation |
240
284
 
241
285
  ### Utilities
@@ -248,6 +292,7 @@ const model = getRecommendedModel('COST_EFFECTIVE', ['openai', 'cloudflare']);
248
292
  | `CostTracker` | Per-provider cost accumulation and budget alerts |
249
293
  | `CreditLedger` | Monthly budgets, rate limits, burn rate projection, threshold events |
250
294
  | `CostOptimizer` | Static methods for optimal provider selection |
295
+ | `MODEL_CATALOG` | Declarative model metadata for routing and recommendation |
251
296
  | `ImageProvider` | Multi-provider image generation (Cloudflare SDXL/FLUX, Google Gemini) |
252
297
 
253
298
  ### Logger
@@ -268,6 +313,7 @@ const model = getRecommendedModel('COST_EFFECTIVE', ['openai', 'cloudflare']);
268
313
  | `ProviderFactoryConfig` | Factory config: provider configs, fallback rules, ledger, logger |
269
314
  | `CostAnalytics` | Cost breakdown, total, and recommendations |
270
315
  | `ProviderHealthEntry` | Health status, metrics, circuit breaker state, capabilities |
316
+ | `ModelCatalogEntry` | Declarative model metadata: provider, lifecycle, capabilities, use cases |
271
317
 
272
318
  ### Factory Functions
273
319
 
@@ -276,7 +322,8 @@ const model = getRecommendedModel('COST_EFFECTIVE', ['openai', 'cloudflare']);
276
322
  | `createLLMProviders(config)` | Create an `LLMProviders` instance |
277
323
  | `createCostOptimizedLLMProviders(config)` | Create with cost optimization, circuit breakers, and retries enabled |
278
324
  | `LLMProviders.fromEnv(env)` | Auto-discover providers from environment variables |
279
- | `getRecommendedModel(useCase, providers)` | Pick the best model for a use case |
325
+ | `llm.getRecommendedModel(request, useCase?)` | Runtime recommendation using configured providers, health, and ledger state |
326
+ | `getRecommendedModel(useCase, providers, context?)` | Pick the best active model for a use case |
280
327
  | `retry(fn, config)` | One-shot retry wrapper for any async function |
281
328
 
282
329
  ## License
package/dist/errors.d.ts CHANGED
@@ -56,6 +56,20 @@ export declare class ToolLoopLimitError extends LLMProviderError {
56
56
  export declare class ToolLoopAbortedError extends LLMProviderError {
57
57
  constructor(provider: string, message?: string);
58
58
  }
59
+ /**
60
+ * Thrown when a provider's response envelope fails runtime schema validation.
61
+ *
62
+ * Indicates the upstream API silently changed shape - a field was renamed,
63
+ * removed, or had its type changed. Non-retryable: retrying hits the same
64
+ * broken shape. The factory treats this as fallback-eligible so traffic
65
+ * routes to a healthy provider while the drift is investigated.
66
+ */
67
+ export declare class SchemaDriftError extends LLMProviderError {
68
+ path: string;
69
+ expected: string;
70
+ actual: string;
71
+ constructor(provider: string, path: string, expected: string, actual: string);
72
+ }
59
73
  /**
60
74
  * Error factory for creating provider-specific errors from HTTP responses
61
75
  */
@@ -1 +1 @@
1
- {"version":3,"file":"errors.d.ts","sourceRoot":"","sources":["../src/errors.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"errors.d.ts","sourceRoot":"","sources":["../src/errors.ts"],"names":[],"mappings":"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"}
package/dist/errors.js CHANGED
@@ -95,6 +95,25 @@ export class ToolLoopAbortedError extends LLMProviderError {
95
95
  super(message, 'TOOL_LOOP_ABORTED', provider, false, 400);
96
96
  }
97
97
  }
98
+ /**
99
+ * Thrown when a provider's response envelope fails runtime schema validation.
100
+ *
101
+ * Indicates the upstream API silently changed shape - a field was renamed,
102
+ * removed, or had its type changed. Non-retryable: retrying hits the same
103
+ * broken shape. The factory treats this as fallback-eligible so traffic
104
+ * routes to a healthy provider while the drift is investigated.
105
+ */
106
+ export class SchemaDriftError extends LLMProviderError {
107
+ path;
108
+ expected;
109
+ actual;
110
+ constructor(provider, path, expected, actual) {
111
+ super(`Response schema drift at ${path}: expected ${expected}, got ${actual}`, 'SCHEMA_DRIFT', provider, false, 422);
112
+ this.path = path;
113
+ this.expected = expected;
114
+ this.actual = actual;
115
+ }
116
+ }
98
117
  export class LLMErrorFactory {
99
118
  static fromHttpResponse(provider, statusCode, responseBody, message) {
100
119
  const defaultMessage = message || responseBody?.message || responseBody?.error?.message || 'Unknown error';
@@ -1 +1 @@
1
- {"version":3,"file":"errors.js","sourceRoot":"","sources":["../src/errors.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"errors.js","sourceRoot":"","sources":["../src/errors.ts"],"names":[],"mappings":"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"}
package/dist/factory.d.ts CHANGED
@@ -7,12 +7,14 @@ import type { Logger } from './utils/logger';
7
7
  import type { ObservabilityHooks } from './utils/hooks';
8
8
  import type { ProviderCostBreakdownEntry } from './utils/cost-tracker';
9
9
  import type { CreditLedger } from './utils/credit-ledger';
10
+ import { type ModelRecommendationUseCase } from './model-catalog';
10
11
  export interface ProviderFactoryConfig {
11
12
  openai?: OpenAIConfig;
12
13
  anthropic?: AnthropicConfig;
13
14
  cloudflare?: CloudflareConfig;
14
15
  cerebras?: CerebrasConfig;
15
16
  groq?: GroqConfig;
17
+ preferredProvider?: 'openai' | 'anthropic' | 'cloudflare' | 'cerebras' | 'groq' | 'auto';
16
18
  defaultProvider?: 'openai' | 'anthropic' | 'cloudflare' | 'cerebras' | 'groq' | 'auto';
17
19
  fallbackRules?: FallbackRule[];
18
20
  costOptimization?: boolean;
@@ -65,13 +67,13 @@ export declare class LLMProviderFactory {
65
67
  analyzeImage(input: AnalyzeImageInput): Promise<LLMResponse>;
66
68
  getProviderBalance(provider?: string): Promise<ProviderBalance | Record<string, ProviderBalance>>;
67
69
  /**
68
- * Build provider chain based on request and configuration
70
+ * Recommend a model dynamically from the declarative catalog.
69
71
  */
70
- private buildProviderChain;
72
+ getRecommendedModel(request: LLMRequest, useCase?: ModelRecommendationUseCase): string;
71
73
  /**
72
- * Get prioritized list of providers based on cost optimization and capabilities
74
+ * Build provider chain and provider-specific default models from the catalog.
73
75
  */
74
- private getPrioritizedProviders;
76
+ private buildProviderPlan;
75
77
  /**
76
78
  * Get appropriate provider for a specific model
77
79
  */
@@ -136,6 +138,8 @@ export declare class LLMProviderFactory {
136
138
  private parseJsonResponse;
137
139
  private getDefaultVisionModel;
138
140
  private providerSupportsVision;
141
+ private getSelectionHealth;
142
+ private resolveUseCase;
139
143
  private getSingleProviderBalance;
140
144
  private getLedgerBalance;
141
145
  private isLedgerLimited;
@@ -1 +1 @@
1
- {"version":3,"file":"factory.d.ts","sourceRoot":"","sources":["../src/factory.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"factory.d.ts","sourceRoot":"","sources":["../src/factory.ts"],"names":[],"mappings":"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"}
package/dist/factory.js CHANGED
@@ -13,7 +13,8 @@ import { CostTracker, defaultCostTracker } from './utils/cost-tracker';
13
13
  import { defaultCircuitBreakerManager } from './utils/circuit-breaker';
14
14
  import { defaultExhaustionRegistry } from './utils/exhaustion';
15
15
  import { defaultLatencyHistogram } from './utils/latency-histogram';
16
- import { LLMProviderError, ConfigurationError, CircuitBreakerOpenError, AuthenticationError, RateLimitError, QuotaExceededError, ToolLoopAbortedError, ToolLoopLimitError, } from './errors';
16
+ import { PROVIDER_FALLBACK_ORDER, getProviderDefaultModel, getProviderForCatalogModel, inferUseCaseFromRequest, rankModels, } from './model-catalog';
17
+ import { LLMProviderError, ConfigurationError, CircuitBreakerOpenError, AuthenticationError, RateLimitError, QuotaExceededError, SchemaDriftError, ToolLoopAbortedError, ToolLoopLimitError, } from './errors';
17
18
  export class LLMProviderFactory {
18
19
  providers = new Map();
19
20
  config;
@@ -73,8 +74,9 @@ export class LLMProviderFactory {
73
74
  * Generate response with intelligent provider selection and fallback
74
75
  */
75
76
  async generateResponse(request) {
76
- const providerChain = this.buildProviderChain(request);
77
- const providerModels = new Map();
77
+ const selectionPlan = this.buildProviderPlan(request);
78
+ const providerChain = selectionPlan.chain;
79
+ const providerModels = selectionPlan.providerModels;
78
80
  let lastError = null;
79
81
  let previousProvider = null;
80
82
  for (let index = 0; index < providerChain.length; index++) {
@@ -167,6 +169,19 @@ export class LLMProviderFactory {
167
169
  timestamp: Date.now(),
168
170
  });
169
171
  }
172
+ // Schema drift — the upstream API silently changed shape. Surface
173
+ // structured telemetry so oncall sees the drift before it cascades.
174
+ if (err instanceof SchemaDriftError) {
175
+ this.hooks.onSchemaDrift?.({
176
+ provider: providerName,
177
+ model: request.model,
178
+ requestId: request.requestId,
179
+ path: err.path,
180
+ expected: err.expected,
181
+ actual: err.actual,
182
+ timestamp: Date.now(),
183
+ });
184
+ }
170
185
  const fallbackDecision = this.getFallbackDecision(error);
171
186
  if (!fallbackDecision.shouldFallback) {
172
187
  throw error;
@@ -178,8 +193,9 @@ export class LLMProviderFactory {
178
193
  throw lastError || new LLMProviderError('All providers failed', 'ALL_PROVIDERS_FAILED', 'factory', false);
179
194
  }
180
195
  async generateResponseStream(request) {
181
- const providerChain = this.buildProviderChain({ ...request, stream: true });
182
- const providerModels = new Map();
196
+ const selectionPlan = this.buildProviderPlan({ ...request, stream: true });
197
+ const providerChain = selectionPlan.chain;
198
+ const providerModels = selectionPlan.providerModels;
183
199
  let lastError = null;
184
200
  let previousProvider = null;
185
201
  for (let index = 0; index < providerChain.length; index++) {
@@ -401,66 +417,82 @@ export class LLMProviderFactory {
401
417
  return result;
402
418
  }
403
419
  /**
404
- * Build provider chain based on request and configuration
420
+ * Recommend a model dynamically from the declarative catalog.
421
+ */
422
+ getRecommendedModel(request, useCase = this.resolveUseCase(request)) {
423
+ const ranked = rankModels(useCase, Array.from(this.providers.keys()), {
424
+ request,
425
+ providerHealth: this.getSelectionHealth(),
426
+ ledger: this.config.ledger,
427
+ });
428
+ if (ranked.length > 0) {
429
+ return ranked[0].model;
430
+ }
431
+ const fallbackProvider = PROVIDER_FALLBACK_ORDER.find(provider => this.providers.has(provider));
432
+ if (!fallbackProvider) {
433
+ throw new ConfigurationError('factory', 'No available providers configured');
434
+ }
435
+ return getProviderDefaultModel(fallbackProvider, request);
436
+ }
437
+ /**
438
+ * Build provider chain and provider-specific default models from the catalog.
405
439
  */
406
- buildProviderChain(request) {
440
+ buildProviderPlan(request) {
407
441
  const chain = [];
442
+ const providerModels = new Map();
443
+ const selectionHealth = this.getSelectionHealth();
444
+ const useCase = this.resolveUseCase(request);
408
445
  // If specific provider requested, try it first
409
446
  if (request.model) {
410
447
  const providerForModel = this.getProviderForModel(request.model);
411
448
  if (providerForModel && this.providers.has(providerForModel)) {
412
449
  chain.push(providerForModel);
450
+ providerModels.set(providerForModel, request.model);
413
451
  }
414
452
  }
415
453
  // Add default provider if different from model provider
416
- const defaultProvider = this.config.defaultProvider || 'auto';
454
+ const defaultProvider = this.config.preferredProvider ?? this.config.defaultProvider ?? 'auto';
417
455
  if (defaultProvider !== 'auto' && !chain.includes(defaultProvider)) {
418
456
  if (this.providers.has(defaultProvider)) {
419
457
  chain.push(defaultProvider);
458
+ if (!request.model) {
459
+ providerModels.set(defaultProvider, getProviderDefaultModel(defaultProvider, request));
460
+ }
420
461
  }
421
462
  }
422
- // For 'auto' mode or as fallbacks, add providers by priority
423
- const prioritizedProviders = this.getPrioritizedProviders(request);
424
- for (const provider of prioritizedProviders) {
425
- if (!chain.includes(provider) && this.providers.has(provider)) {
463
+ const rankedModels = rankModels(useCase, Array.from(this.providers.keys()), {
464
+ request,
465
+ providerHealth: selectionHealth,
466
+ ledger: this.config.ledger,
467
+ });
468
+ for (const candidate of rankedModels) {
469
+ if (!providerModels.has(candidate.provider)) {
470
+ providerModels.set(candidate.provider, candidate.model);
471
+ }
472
+ if (!chain.includes(candidate.provider) && this.providers.has(candidate.provider)) {
473
+ chain.push(candidate.provider);
474
+ }
475
+ }
476
+ for (const provider of PROVIDER_FALLBACK_ORDER) {
477
+ if (!this.providers.has(provider))
478
+ continue;
479
+ if (!chain.includes(provider)) {
426
480
  chain.push(provider);
427
481
  }
482
+ if (!providerModels.has(provider)) {
483
+ providerModels.set(provider, getProviderDefaultModel(provider, request));
484
+ }
428
485
  }
429
- return chain;
430
- }
431
- /**
432
- * Get prioritized list of providers based on cost optimization and capabilities
433
- */
434
- getPrioritizedProviders(request) {
435
- const visionOnly = (request.images?.length ?? 0) > 0;
436
- if (!this.config.costOptimization) {
437
- // Default priority: all configured providers, cheapest first
438
- return ['cloudflare', 'cerebras', 'groq', 'anthropic', 'openai']
439
- .filter(p => this.providers.has(p))
440
- .filter(p => !visionOnly || this.providerSupportsVision(p));
441
- }
442
- // Cost-optimized routing
443
- const providers = Array.from(this.providers.keys())
444
- .filter(p => !visionOnly || this.providerSupportsVision(p));
445
- const sortedProviders = [...providers].sort((a, b) => {
446
- const providerA = this.providers.get(a);
447
- const providerB = this.providers.get(b);
448
- const estimatedCostA = providerA.estimateCost(request);
449
- const estimatedCostB = providerB.estimateCost(request);
450
- if (estimatedCostA !== estimatedCostB) {
451
- return estimatedCostA - estimatedCostB;
452
- }
453
- // If estimates tie, prefer the provider with less accumulated spend.
454
- const trackedCostA = this.costTracker.getProviderCost(a);
455
- const trackedCostB = this.costTracker.getProviderCost(b);
456
- return trackedCostA - trackedCostB;
457
- });
458
- return sortedProviders;
486
+ return { chain, providerModels, useCase };
459
487
  }
460
488
  /**
461
489
  * Get appropriate provider for a specific model
462
490
  */
463
491
  getProviderForModel(model) {
492
+ const catalogProvider = getProviderForCatalogModel(model);
493
+ if (catalogProvider) {
494
+ return catalogProvider;
495
+ }
464
496
  // OpenAI models
465
497
  if (model.startsWith('gpt-')) {
466
498
  return 'openai';
@@ -517,10 +549,16 @@ export class LLMProviderFactory {
517
549
  error instanceof RateLimitError) {
518
550
  return { shouldFallback: true };
519
551
  }
552
+ // Schema drift: provider's response shape changed. Retry won't help;
553
+ // only another provider can. Defense against silent API deprecations.
554
+ if (error instanceof SchemaDriftError) {
555
+ return { shouldFallback: true };
556
+ }
520
557
  if (error instanceof LLMProviderError) {
521
558
  if (error.code === 'SERVER_ERROR' ||
522
559
  error.code === 'NETWORK_ERROR' ||
523
- error.code === 'TIMEOUT') {
560
+ error.code === 'TIMEOUT' ||
561
+ error.code === 'SCHEMA_DRIFT') {
524
562
  return { shouldFallback: true };
525
563
  }
526
564
  }
@@ -834,15 +872,59 @@ export class LLMProviderFactory {
834
872
  getDefaultVisionModel() {
835
873
  if (this.config.defaultVisionModel)
836
874
  return this.config.defaultVisionModel;
837
- if (this.providers.has('anthropic'))
838
- return 'claude-haiku-4-5-20251001';
839
- if (this.providers.has('openai'))
840
- return 'gpt-4o-mini';
875
+ const visionRequest = {
876
+ messages: [{ role: 'user', content: 'Describe this image.' }],
877
+ images: [{}],
878
+ maxTokens: 1
879
+ };
880
+ if (this.providers.has('anthropic')) {
881
+ return getProviderDefaultModel('anthropic', visionRequest);
882
+ }
883
+ if (this.providers.has('openai')) {
884
+ return getProviderDefaultModel('openai', visionRequest);
885
+ }
886
+ if (this.providers.has('cloudflare')) {
887
+ return getProviderDefaultModel('cloudflare', visionRequest);
888
+ }
841
889
  return undefined;
842
890
  }
843
891
  providerSupportsVision(providerName) {
844
892
  return this.providers.get(providerName)?.supportsVision === true;
845
893
  }
894
+ getSelectionHealth() {
895
+ const health = {};
896
+ for (const providerName of this.providers.keys()) {
897
+ const metrics = this.providers.get(providerName)?.getMetrics();
898
+ const circuitBreaker = this.config.enableCircuitBreaker
899
+ ? defaultCircuitBreakerManager.getBreaker(providerName).getState()
900
+ : null;
901
+ health[providerName] = {
902
+ healthy: circuitBreaker?.state !== 'OPEN',
903
+ metrics,
904
+ circuitBreaker,
905
+ };
906
+ }
907
+ return health;
908
+ }
909
+ resolveUseCase(request) {
910
+ const metadataUseCase = request.metadata?.useCase;
911
+ if (typeof metadataUseCase === 'string') {
912
+ const normalized = metadataUseCase.toUpperCase();
913
+ if (normalized === 'COST_EFFECTIVE' ||
914
+ normalized === 'HIGH_PERFORMANCE' ||
915
+ normalized === 'BALANCED' ||
916
+ normalized === 'TOOL_CALLING' ||
917
+ normalized === 'LONG_CONTEXT' ||
918
+ normalized === 'VISION') {
919
+ return normalized;
920
+ }
921
+ }
922
+ const inferredUseCase = inferUseCaseFromRequest(request);
923
+ if (this.config.costOptimization && inferredUseCase === 'BALANCED') {
924
+ return 'COST_EFFECTIVE';
925
+ }
926
+ return inferredUseCase;
927
+ }
846
928
  async getSingleProviderBalance(providerName) {
847
929
  const ledgerBalance = this.getLedgerBalance(providerName);
848
930
  if (ledgerBalance) {