* Merge partial routing config overrides with defaults.
(overrides?: Partial<RoutingConfig>)
| 1368 | * Merge partial routing config overrides with defaults. |
| 1369 | */ |
| 1370 | function mergeRoutingConfig(overrides?: Partial<RoutingConfig>): RoutingConfig { |
| 1371 | if (!overrides) return DEFAULT_ROUTING_CONFIG; |
| 1372 | // Merge tier sets per-tier so users can override a single tier |
| 1373 | // (e.g. just COMPLEX) without having to redefine all four. |
| 1374 | // `null` explicitly disables a tier set (e.g. `agenticTiers: null` forces |
| 1375 | // all requests through regular tiers even when tools are present). |
| 1376 | const mergeTiers = ( |
| 1377 | defaults: RoutingConfig["tiers"] | null | undefined, |
| 1378 | user: Partial<RoutingConfig["tiers"]> | null | undefined, |
| 1379 | ): RoutingConfig["tiers"] | null => { |
| 1380 | if (user === null) return null; |
| 1381 | if (user === undefined) return defaults ?? null; |
| 1382 | return { ...(defaults ?? {}), ...user } as RoutingConfig["tiers"]; |
| 1383 | }; |
| 1384 | return { |
| 1385 | ...DEFAULT_ROUTING_CONFIG, |
| 1386 | ...overrides, |
| 1387 | classifier: { ...DEFAULT_ROUTING_CONFIG.classifier, ...overrides.classifier }, |
| 1388 | scoring: { ...DEFAULT_ROUTING_CONFIG.scoring, ...overrides.scoring }, |
| 1389 | tiers: |
| 1390 | mergeTiers(DEFAULT_ROUTING_CONFIG.tiers, overrides.tiers) ?? DEFAULT_ROUTING_CONFIG.tiers, |
| 1391 | agenticTiers: mergeTiers(DEFAULT_ROUTING_CONFIG.agenticTiers, overrides.agenticTiers), |
| 1392 | ecoTiers: mergeTiers(DEFAULT_ROUTING_CONFIG.ecoTiers, overrides.ecoTiers), |
| 1393 | premiumTiers: mergeTiers(DEFAULT_ROUTING_CONFIG.premiumTiers, overrides.premiumTiers), |
| 1394 | overrides: { ...DEFAULT_ROUTING_CONFIG.overrides, ...overrides.overrides }, |
| 1395 | }; |
| 1396 | } |
| 1397 | |
| 1398 | /** |
| 1399 | * Build the `usage.cost` breakdown that ClawRouter injects into responses. |
no test coverage detected