@dexto/core 1.5.5 → 1.5.7

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 (146) hide show
  1. package/dist/agent/DextoAgent.cjs +94 -26
  2. package/dist/agent/DextoAgent.d.ts +17 -7
  3. package/dist/agent/DextoAgent.d.ts.map +1 -1
  4. package/dist/agent/DextoAgent.js +95 -27
  5. package/dist/agent/schemas.d.ts +417 -66
  6. package/dist/agent/schemas.d.ts.map +1 -1
  7. package/dist/context/utils.cjs +49 -3
  8. package/dist/context/utils.d.ts.map +1 -1
  9. package/dist/context/utils.js +49 -3
  10. package/dist/errors/types.cjs +2 -1
  11. package/dist/errors/types.d.ts +2 -1
  12. package/dist/errors/types.d.ts.map +1 -1
  13. package/dist/errors/types.js +2 -1
  14. package/dist/image/types.d.ts +15 -0
  15. package/dist/image/types.d.ts.map +1 -1
  16. package/dist/llm/error-codes.cjs +1 -0
  17. package/dist/llm/error-codes.d.ts +1 -0
  18. package/dist/llm/error-codes.d.ts.map +1 -1
  19. package/dist/llm/error-codes.js +1 -0
  20. package/dist/llm/errors.cjs +15 -0
  21. package/dist/llm/errors.d.ts +15 -8
  22. package/dist/llm/errors.d.ts.map +1 -1
  23. package/dist/llm/errors.js +15 -0
  24. package/dist/llm/executor/turn-executor.cjs +27 -0
  25. package/dist/llm/executor/turn-executor.d.ts.map +1 -1
  26. package/dist/llm/executor/turn-executor.js +27 -0
  27. package/dist/llm/registry.cjs +472 -28
  28. package/dist/llm/registry.d.ts +80 -4
  29. package/dist/llm/registry.d.ts.map +1 -1
  30. package/dist/llm/registry.js +464 -25
  31. package/dist/llm/resolver.cjs +13 -0
  32. package/dist/llm/resolver.d.ts.map +1 -1
  33. package/dist/llm/resolver.js +16 -1
  34. package/dist/llm/schemas.d.ts +59 -59
  35. package/dist/llm/services/factory.cjs +41 -25
  36. package/dist/llm/services/factory.d.ts +20 -1
  37. package/dist/llm/services/factory.d.ts.map +1 -1
  38. package/dist/llm/services/factory.js +42 -26
  39. package/dist/llm/services/test-utils.integration.cjs +5 -1
  40. package/dist/llm/services/test-utils.integration.d.ts.map +1 -1
  41. package/dist/llm/services/test-utils.integration.js +5 -1
  42. package/dist/llm/types.cjs +5 -2
  43. package/dist/llm/types.d.ts +1 -1
  44. package/dist/llm/types.d.ts.map +1 -1
  45. package/dist/llm/types.js +5 -2
  46. package/dist/logger/logger.cjs +6 -7
  47. package/dist/logger/logger.d.ts +1 -0
  48. package/dist/logger/logger.d.ts.map +1 -1
  49. package/dist/logger/logger.js +6 -7
  50. package/dist/logger/v2/dexto-logger.cjs +4 -0
  51. package/dist/logger/v2/dexto-logger.d.ts +3 -0
  52. package/dist/logger/v2/dexto-logger.d.ts.map +1 -1
  53. package/dist/logger/v2/dexto-logger.js +4 -0
  54. package/dist/logger/v2/types.d.ts +2 -0
  55. package/dist/logger/v2/types.d.ts.map +1 -1
  56. package/dist/mcp/error-codes.cjs +1 -0
  57. package/dist/mcp/error-codes.d.ts +1 -0
  58. package/dist/mcp/error-codes.d.ts.map +1 -1
  59. package/dist/mcp/error-codes.js +1 -0
  60. package/dist/mcp/errors.cjs +13 -0
  61. package/dist/mcp/errors.d.ts +7 -0
  62. package/dist/mcp/errors.d.ts.map +1 -1
  63. package/dist/mcp/errors.js +13 -0
  64. package/dist/mcp/manager.cjs +46 -4
  65. package/dist/mcp/manager.d.ts +10 -2
  66. package/dist/mcp/manager.d.ts.map +1 -1
  67. package/dist/mcp/manager.js +46 -4
  68. package/dist/mcp/mcp-client.cjs +89 -5
  69. package/dist/mcp/mcp-client.d.ts +5 -1
  70. package/dist/mcp/mcp-client.d.ts.map +1 -1
  71. package/dist/mcp/mcp-client.js +89 -5
  72. package/dist/mcp/schemas.cjs +6 -1
  73. package/dist/mcp/schemas.d.ts +1 -1
  74. package/dist/mcp/schemas.d.ts.map +1 -1
  75. package/dist/mcp/schemas.js +6 -1
  76. package/dist/mcp/types.d.ts +5 -0
  77. package/dist/mcp/types.d.ts.map +1 -1
  78. package/dist/prompts/index.d.ts +1 -1
  79. package/dist/prompts/index.d.ts.map +1 -1
  80. package/dist/prompts/prompt-manager.cjs +90 -4
  81. package/dist/prompts/prompt-manager.d.ts +16 -6
  82. package/dist/prompts/prompt-manager.d.ts.map +1 -1
  83. package/dist/prompts/prompt-manager.js +90 -4
  84. package/dist/prompts/providers/config-prompt-provider.cjs +104 -10
  85. package/dist/prompts/providers/config-prompt-provider.d.ts.map +1 -1
  86. package/dist/prompts/providers/config-prompt-provider.js +105 -11
  87. package/dist/prompts/providers/custom-prompt-provider.cjs +1 -0
  88. package/dist/prompts/providers/custom-prompt-provider.d.ts.map +1 -1
  89. package/dist/prompts/providers/custom-prompt-provider.js +1 -0
  90. package/dist/prompts/providers/mcp-prompt-provider.cjs +1 -0
  91. package/dist/prompts/providers/mcp-prompt-provider.d.ts.map +1 -1
  92. package/dist/prompts/providers/mcp-prompt-provider.js +1 -0
  93. package/dist/prompts/schemas.cjs +28 -2
  94. package/dist/prompts/schemas.d.ts +130 -0
  95. package/dist/prompts/schemas.d.ts.map +1 -1
  96. package/dist/prompts/schemas.js +28 -2
  97. package/dist/prompts/types.d.ts +55 -3
  98. package/dist/prompts/types.d.ts.map +1 -1
  99. package/dist/session/chat-session.d.ts +1 -1
  100. package/dist/session/chat-session.d.ts.map +1 -1
  101. package/dist/session/index.d.ts +1 -1
  102. package/dist/session/index.d.ts.map +1 -1
  103. package/dist/session/session-manager.cjs +47 -3
  104. package/dist/session/session-manager.d.ts +10 -0
  105. package/dist/session/session-manager.d.ts.map +1 -1
  106. package/dist/session/session-manager.js +47 -3
  107. package/dist/systemPrompt/contributors.cjs +42 -0
  108. package/dist/systemPrompt/contributors.d.ts +13 -0
  109. package/dist/systemPrompt/contributors.d.ts.map +1 -1
  110. package/dist/systemPrompt/contributors.js +41 -0
  111. package/dist/tools/errors.cjs +7 -3
  112. package/dist/tools/errors.d.ts +5 -1
  113. package/dist/tools/errors.d.ts.map +1 -1
  114. package/dist/tools/errors.js +7 -3
  115. package/dist/tools/internal-tools/constants.cjs +2 -1
  116. package/dist/tools/internal-tools/constants.d.ts +1 -1
  117. package/dist/tools/internal-tools/constants.d.ts.map +1 -1
  118. package/dist/tools/internal-tools/constants.js +2 -1
  119. package/dist/tools/internal-tools/implementations/invoke-skill-tool.cjs +140 -0
  120. package/dist/tools/internal-tools/implementations/invoke-skill-tool.d.ts +24 -0
  121. package/dist/tools/internal-tools/implementations/invoke-skill-tool.d.ts.map +1 -0
  122. package/dist/tools/internal-tools/implementations/invoke-skill-tool.js +117 -0
  123. package/dist/tools/internal-tools/provider.cjs +15 -0
  124. package/dist/tools/internal-tools/provider.d.ts +12 -0
  125. package/dist/tools/internal-tools/provider.d.ts.map +1 -1
  126. package/dist/tools/internal-tools/provider.js +15 -0
  127. package/dist/tools/internal-tools/registry.cjs +6 -0
  128. package/dist/tools/internal-tools/registry.d.ts +34 -0
  129. package/dist/tools/internal-tools/registry.d.ts.map +1 -1
  130. package/dist/tools/internal-tools/registry.js +6 -0
  131. package/dist/tools/schemas.cjs +2 -2
  132. package/dist/tools/schemas.d.ts +1 -1
  133. package/dist/tools/schemas.d.ts.map +1 -1
  134. package/dist/tools/schemas.js +2 -2
  135. package/dist/tools/tool-manager.cjs +230 -79
  136. package/dist/tools/tool-manager.d.ts +89 -8
  137. package/dist/tools/tool-manager.d.ts.map +1 -1
  138. package/dist/tools/tool-manager.js +231 -80
  139. package/dist/utils/api-key-resolver.cjs +5 -2
  140. package/dist/utils/api-key-resolver.d.ts.map +1 -1
  141. package/dist/utils/api-key-resolver.js +5 -2
  142. package/dist/utils/service-initializer.cjs +8 -2
  143. package/dist/utils/service-initializer.d.ts +5 -1
  144. package/dist/utils/service-initializer.d.ts.map +1 -1
  145. package/dist/utils/service-initializer.js +8 -2
  146. package/package.json +1 -1
@@ -2,6 +2,7 @@ import "../chunk-PTJYTZNU.js";
2
2
  import { LLMError } from "./errors.js";
3
3
  import { LLMErrorCode } from "./error-codes.js";
4
4
  import { DextoRuntimeError } from "../errors/DextoRuntimeError.js";
5
+ import { ErrorScope, ErrorType } from "../errors/types.js";
5
6
  import {
6
7
  LLM_PROVIDERS
7
8
  } from "./types.js";
@@ -35,6 +36,7 @@ const LLM_REGISTRY = {
35
36
  {
36
37
  name: "gpt-5.2-chat-latest",
37
38
  displayName: "GPT-5.2 Instant",
39
+ openrouterId: "openai/gpt-5.2-chat",
38
40
  maxInputTokens: 4e5,
39
41
  supportedFileTypes: ["pdf", "image"],
40
42
  pricing: {
@@ -48,6 +50,7 @@ const LLM_REGISTRY = {
48
50
  {
49
51
  name: "gpt-5.2",
50
52
  displayName: "GPT-5.2 Thinking",
53
+ openrouterId: "openai/gpt-5.2",
51
54
  maxInputTokens: 4e5,
52
55
  supportedFileTypes: ["pdf", "image"],
53
56
  pricing: {
@@ -61,6 +64,7 @@ const LLM_REGISTRY = {
61
64
  {
62
65
  name: "gpt-5.2-pro",
63
66
  displayName: "GPT-5.2 Pro",
67
+ openrouterId: "openai/gpt-5.2-pro",
64
68
  maxInputTokens: 4e5,
65
69
  supportedFileTypes: ["pdf", "image"],
66
70
  pricing: {
@@ -74,6 +78,7 @@ const LLM_REGISTRY = {
74
78
  {
75
79
  name: "gpt-5.2-codex",
76
80
  displayName: "GPT-5.2 Codex",
81
+ openrouterId: "openai/gpt-5.2-codex",
77
82
  maxInputTokens: 4e5,
78
83
  supportedFileTypes: ["pdf", "image"],
79
84
  pricing: {
@@ -88,6 +93,7 @@ const LLM_REGISTRY = {
88
93
  {
89
94
  name: "gpt-5.1-chat-latest",
90
95
  displayName: "GPT-5.1 Instant",
96
+ openrouterId: "openai/gpt-5.1-chat",
91
97
  maxInputTokens: 4e5,
92
98
  supportedFileTypes: ["pdf", "image"],
93
99
  pricing: {
@@ -101,6 +107,7 @@ const LLM_REGISTRY = {
101
107
  {
102
108
  name: "gpt-5.1",
103
109
  displayName: "GPT-5.1 Thinking",
110
+ openrouterId: "openai/gpt-5.1",
104
111
  maxInputTokens: 4e5,
105
112
  supportedFileTypes: ["pdf", "image"],
106
113
  pricing: {
@@ -114,6 +121,7 @@ const LLM_REGISTRY = {
114
121
  {
115
122
  name: "gpt-5.1-codex",
116
123
  displayName: "GPT-5.1 Codex",
124
+ openrouterId: "openai/gpt-5.1-codex",
117
125
  maxInputTokens: 4e5,
118
126
  supportedFileTypes: ["pdf", "image"],
119
127
  pricing: {
@@ -127,6 +135,7 @@ const LLM_REGISTRY = {
127
135
  {
128
136
  name: "gpt-5.1-codex-mini",
129
137
  displayName: "GPT-5.1 Codex Mini",
138
+ openrouterId: "openai/gpt-5.1-codex-mini",
130
139
  maxInputTokens: 4e5,
131
140
  supportedFileTypes: ["pdf", "image"],
132
141
  pricing: {
@@ -153,6 +162,7 @@ const LLM_REGISTRY = {
153
162
  {
154
163
  name: "gpt-5-pro",
155
164
  displayName: "GPT-5 Pro",
165
+ openrouterId: "openai/gpt-5-pro",
156
166
  maxInputTokens: 4e5,
157
167
  supportedFileTypes: ["pdf", "image"],
158
168
  pricing: {
@@ -166,6 +176,7 @@ const LLM_REGISTRY = {
166
176
  {
167
177
  name: "gpt-5",
168
178
  displayName: "GPT-5",
179
+ openrouterId: "openai/gpt-5",
169
180
  maxInputTokens: 4e5,
170
181
  supportedFileTypes: ["pdf", "image"],
171
182
  pricing: {
@@ -179,6 +190,7 @@ const LLM_REGISTRY = {
179
190
  {
180
191
  name: "gpt-5-mini",
181
192
  displayName: "GPT-5 Mini",
193
+ openrouterId: "openai/gpt-5-mini",
182
194
  maxInputTokens: 4e5,
183
195
  default: true,
184
196
  supportedFileTypes: ["pdf", "image"],
@@ -193,6 +205,7 @@ const LLM_REGISTRY = {
193
205
  {
194
206
  name: "gpt-5-nano",
195
207
  displayName: "GPT-5 Nano",
208
+ openrouterId: "openai/gpt-5-nano",
196
209
  maxInputTokens: 4e5,
197
210
  supportedFileTypes: ["pdf", "image"],
198
211
  pricing: {
@@ -206,6 +219,7 @@ const LLM_REGISTRY = {
206
219
  {
207
220
  name: "gpt-5-codex",
208
221
  displayName: "GPT-5 Codex",
222
+ openrouterId: "openai/gpt-5-codex",
209
223
  maxInputTokens: 4e5,
210
224
  supportedFileTypes: ["pdf", "image"],
211
225
  pricing: {
@@ -219,6 +233,7 @@ const LLM_REGISTRY = {
219
233
  {
220
234
  name: "gpt-4.1",
221
235
  displayName: "GPT-4.1",
236
+ openrouterId: "openai/gpt-4.1",
222
237
  maxInputTokens: 1048576,
223
238
  supportedFileTypes: ["pdf", "image"],
224
239
  pricing: {
@@ -232,6 +247,7 @@ const LLM_REGISTRY = {
232
247
  {
233
248
  name: "gpt-4.1-mini",
234
249
  displayName: "GPT-4.1 Mini",
250
+ openrouterId: "openai/gpt-4.1-mini",
235
251
  maxInputTokens: 1048576,
236
252
  supportedFileTypes: ["pdf", "image"],
237
253
  pricing: {
@@ -245,6 +261,7 @@ const LLM_REGISTRY = {
245
261
  {
246
262
  name: "gpt-4.1-nano",
247
263
  displayName: "GPT-4.1 Nano",
264
+ openrouterId: "openai/gpt-4.1-nano",
248
265
  maxInputTokens: 1048576,
249
266
  supportedFileTypes: ["pdf", "image"],
250
267
  pricing: {
@@ -258,6 +275,7 @@ const LLM_REGISTRY = {
258
275
  {
259
276
  name: "gpt-4o",
260
277
  displayName: "GPT-4o",
278
+ openrouterId: "openai/gpt-4o",
261
279
  maxInputTokens: 128e3,
262
280
  supportedFileTypes: ["pdf", "image"],
263
281
  pricing: {
@@ -271,6 +289,7 @@ const LLM_REGISTRY = {
271
289
  {
272
290
  name: "gpt-4o-mini",
273
291
  displayName: "GPT-4o Mini",
292
+ openrouterId: "openai/gpt-4o-mini",
274
293
  maxInputTokens: 128e3,
275
294
  supportedFileTypes: ["pdf", "image"],
276
295
  pricing: {
@@ -284,6 +303,7 @@ const LLM_REGISTRY = {
284
303
  {
285
304
  name: "gpt-4o-audio-preview",
286
305
  displayName: "GPT-4o Audio Preview",
306
+ openrouterId: "openai/gpt-4o-audio-preview",
287
307
  maxInputTokens: 128e3,
288
308
  supportedFileTypes: ["audio"],
289
309
  pricing: {
@@ -297,6 +317,7 @@ const LLM_REGISTRY = {
297
317
  {
298
318
  name: "o4-mini",
299
319
  displayName: "O4 Mini",
320
+ openrouterId: "openai/o4-mini",
300
321
  maxInputTokens: 2e5,
301
322
  supportedFileTypes: ["pdf", "image"],
302
323
  pricing: {
@@ -310,6 +331,7 @@ const LLM_REGISTRY = {
310
331
  {
311
332
  name: "o3",
312
333
  displayName: "O3",
334
+ openrouterId: "openai/o3",
313
335
  maxInputTokens: 2e5,
314
336
  supportedFileTypes: ["pdf", "image"],
315
337
  pricing: {
@@ -323,6 +345,7 @@ const LLM_REGISTRY = {
323
345
  {
324
346
  name: "o3-mini",
325
347
  displayName: "O3 Mini",
348
+ openrouterId: "openai/o3-mini",
326
349
  maxInputTokens: 2e5,
327
350
  supportedFileTypes: [],
328
351
  pricing: {
@@ -336,6 +359,7 @@ const LLM_REGISTRY = {
336
359
  {
337
360
  name: "o1",
338
361
  displayName: "O1",
362
+ openrouterId: "openai/o1",
339
363
  maxInputTokens: 2e5,
340
364
  supportedFileTypes: ["pdf", "image"],
341
365
  pricing: {
@@ -348,8 +372,9 @@ const LLM_REGISTRY = {
348
372
  }
349
373
  ],
350
374
  baseURLSupport: "none",
351
- supportedFileTypes: []
375
+ supportedFileTypes: [],
352
376
  // No defaults - models must explicitly specify support
377
+ openrouterPrefix: "openai"
353
378
  },
354
379
  "openai-compatible": {
355
380
  models: [],
@@ -364,6 +389,7 @@ const LLM_REGISTRY = {
364
389
  {
365
390
  name: "claude-haiku-4-5-20251001",
366
391
  displayName: "Claude 4.5 Haiku",
392
+ openrouterId: "anthropic/claude-haiku-4.5",
367
393
  maxInputTokens: 2e5,
368
394
  default: true,
369
395
  supportedFileTypes: ["pdf", "image"],
@@ -379,6 +405,7 @@ const LLM_REGISTRY = {
379
405
  {
380
406
  name: "claude-sonnet-4-5-20250929",
381
407
  displayName: "Claude 4.5 Sonnet",
408
+ openrouterId: "anthropic/claude-sonnet-4.5",
382
409
  maxInputTokens: 2e5,
383
410
  supportedFileTypes: ["pdf", "image"],
384
411
  pricing: {
@@ -393,6 +420,7 @@ const LLM_REGISTRY = {
393
420
  {
394
421
  name: "claude-opus-4-5-20251101",
395
422
  displayName: "Claude 4.5 Opus",
423
+ openrouterId: "anthropic/claude-opus-4.5",
396
424
  maxInputTokens: 2e5,
397
425
  supportedFileTypes: ["pdf", "image"],
398
426
  pricing: {
@@ -407,6 +435,7 @@ const LLM_REGISTRY = {
407
435
  {
408
436
  name: "claude-opus-4-1-20250805",
409
437
  displayName: "Claude 4.1 Opus",
438
+ openrouterId: "anthropic/claude-opus-4.1",
410
439
  maxInputTokens: 2e5,
411
440
  supportedFileTypes: ["pdf", "image"],
412
441
  pricing: {
@@ -421,6 +450,7 @@ const LLM_REGISTRY = {
421
450
  {
422
451
  name: "claude-4-opus-20250514",
423
452
  displayName: "Claude 4 Opus",
453
+ openrouterId: "anthropic/claude-opus-4",
424
454
  maxInputTokens: 2e5,
425
455
  supportedFileTypes: ["pdf", "image"],
426
456
  pricing: {
@@ -435,6 +465,7 @@ const LLM_REGISTRY = {
435
465
  {
436
466
  name: "claude-4-sonnet-20250514",
437
467
  displayName: "Claude 4 Sonnet",
468
+ openrouterId: "anthropic/claude-sonnet-4",
438
469
  maxInputTokens: 2e5,
439
470
  supportedFileTypes: ["pdf", "image"],
440
471
  pricing: {
@@ -449,6 +480,7 @@ const LLM_REGISTRY = {
449
480
  {
450
481
  name: "claude-3-7-sonnet-20250219",
451
482
  displayName: "Claude 3.7 Sonnet",
483
+ openrouterId: "anthropic/claude-3.7-sonnet",
452
484
  maxInputTokens: 2e5,
453
485
  supportedFileTypes: ["pdf", "image"],
454
486
  pricing: {
@@ -463,6 +495,7 @@ const LLM_REGISTRY = {
463
495
  {
464
496
  name: "claude-3-5-sonnet-20240620",
465
497
  displayName: "Claude 3.5 Sonnet",
498
+ openrouterId: "anthropic/claude-3.5-sonnet",
466
499
  maxInputTokens: 2e5,
467
500
  supportedFileTypes: ["pdf", "image"],
468
501
  pricing: {
@@ -477,6 +510,7 @@ const LLM_REGISTRY = {
477
510
  {
478
511
  name: "claude-3-5-haiku-20241022",
479
512
  displayName: "Claude 3.5 Haiku",
513
+ openrouterId: "anthropic/claude-3.5-haiku",
480
514
  maxInputTokens: 2e5,
481
515
  supportedFileTypes: ["pdf", "image"],
482
516
  pricing: {
@@ -490,14 +524,16 @@ const LLM_REGISTRY = {
490
524
  }
491
525
  ],
492
526
  baseURLSupport: "none",
493
- supportedFileTypes: []
527
+ supportedFileTypes: [],
494
528
  // No defaults - models must explicitly specify support
529
+ openrouterPrefix: "anthropic"
495
530
  },
496
531
  google: {
497
532
  models: [
498
533
  {
499
534
  name: "gemini-3-flash-preview",
500
535
  displayName: "Gemini 3 Flash Preview",
536
+ openrouterId: "google/gemini-3-flash-preview",
501
537
  maxInputTokens: 1048576,
502
538
  default: true,
503
539
  supportedFileTypes: ["pdf", "image", "audio"],
@@ -512,6 +548,7 @@ const LLM_REGISTRY = {
512
548
  {
513
549
  name: "gemini-3-pro-preview",
514
550
  displayName: "Gemini 3 Pro Preview",
551
+ openrouterId: "google/gemini-3-pro-preview",
515
552
  maxInputTokens: 1048576,
516
553
  supportedFileTypes: ["pdf", "image", "audio"],
517
554
  pricing: {
@@ -525,6 +562,7 @@ const LLM_REGISTRY = {
525
562
  {
526
563
  name: "gemini-3-pro-image-preview",
527
564
  displayName: "Gemini 3 Pro Image Preview",
565
+ openrouterId: "google/gemini-3-pro-image-preview",
528
566
  maxInputTokens: 1048576,
529
567
  supportedFileTypes: ["image"],
530
568
  pricing: {
@@ -538,6 +576,7 @@ const LLM_REGISTRY = {
538
576
  {
539
577
  name: "gemini-2.5-pro",
540
578
  displayName: "Gemini 2.5 Pro",
579
+ openrouterId: "google/gemini-2.5-pro",
541
580
  maxInputTokens: 1048576,
542
581
  supportedFileTypes: ["pdf", "image", "audio"],
543
582
  pricing: {
@@ -551,6 +590,7 @@ const LLM_REGISTRY = {
551
590
  {
552
591
  name: "gemini-2.5-flash",
553
592
  displayName: "Gemini 2.5 Flash",
593
+ openrouterId: "google/gemini-2.5-flash",
554
594
  maxInputTokens: 1048576,
555
595
  supportedFileTypes: ["pdf", "image", "audio"],
556
596
  pricing: {
@@ -564,6 +604,7 @@ const LLM_REGISTRY = {
564
604
  {
565
605
  name: "gemini-2.5-flash-lite",
566
606
  displayName: "Gemini 2.5 Flash Lite",
607
+ openrouterId: "google/gemini-2.5-flash-lite",
567
608
  maxInputTokens: 1048576,
568
609
  supportedFileTypes: ["pdf", "image", "audio"],
569
610
  pricing: {
@@ -577,6 +618,7 @@ const LLM_REGISTRY = {
577
618
  {
578
619
  name: "gemini-2.0-flash",
579
620
  displayName: "Gemini 2.0 Flash",
621
+ openrouterId: "google/gemini-2.0-flash-001",
580
622
  maxInputTokens: 1048576,
581
623
  supportedFileTypes: ["pdf", "image", "audio"],
582
624
  pricing: {
@@ -591,6 +633,7 @@ const LLM_REGISTRY = {
591
633
  {
592
634
  name: "gemini-2.0-flash-lite",
593
635
  displayName: "Gemini 2.0 Flash Lite",
636
+ openrouterId: "google/gemini-2.0-flash-lite-001",
594
637
  maxInputTokens: 1048576,
595
638
  supportedFileTypes: ["pdf", "image", "audio"],
596
639
  pricing: {
@@ -603,8 +646,9 @@ const LLM_REGISTRY = {
603
646
  }
604
647
  ],
605
648
  baseURLSupport: "none",
606
- supportedFileTypes: []
649
+ supportedFileTypes: [],
607
650
  // No defaults - models must explicitly specify support
651
+ openrouterPrefix: "google"
608
652
  },
609
653
  // https://console.groq.com/docs/models
610
654
  groq: {
@@ -731,6 +775,7 @@ const LLM_REGISTRY = {
731
775
  {
732
776
  name: "grok-4",
733
777
  displayName: "Grok 4",
778
+ openrouterId: "x-ai/grok-4",
734
779
  maxInputTokens: 256e3,
735
780
  default: true,
736
781
  supportedFileTypes: ["image"],
@@ -745,6 +790,7 @@ const LLM_REGISTRY = {
745
790
  {
746
791
  name: "grok-3",
747
792
  displayName: "Grok 3",
793
+ openrouterId: "x-ai/grok-3",
748
794
  maxInputTokens: 131072,
749
795
  supportedFileTypes: ["image"],
750
796
  pricing: {
@@ -758,6 +804,7 @@ const LLM_REGISTRY = {
758
804
  {
759
805
  name: "grok-3-mini",
760
806
  displayName: "Grok 3 Mini",
807
+ openrouterId: "x-ai/grok-3-mini",
761
808
  maxInputTokens: 131072,
762
809
  supportedFileTypes: ["image"],
763
810
  pricing: {
@@ -771,6 +818,7 @@ const LLM_REGISTRY = {
771
818
  {
772
819
  name: "grok-code-fast-1",
773
820
  displayName: "Grok Code Fast",
821
+ openrouterId: "x-ai/grok-code-fast-1",
774
822
  maxInputTokens: 131072,
775
823
  supportedFileTypes: [],
776
824
  pricing: {
@@ -783,8 +831,9 @@ const LLM_REGISTRY = {
783
831
  }
784
832
  ],
785
833
  baseURLSupport: "none",
786
- supportedFileTypes: []
834
+ supportedFileTypes: [],
787
835
  // XAI currently doesn't support file uploads
836
+ openrouterPrefix: "x-ai"
788
837
  },
789
838
  // https://docs.cohere.com/reference/models
790
839
  cohere: {
@@ -792,6 +841,7 @@ const LLM_REGISTRY = {
792
841
  {
793
842
  name: "command-a-03-2025",
794
843
  displayName: "Command A (03-2025)",
844
+ openrouterId: "cohere/command-a",
795
845
  maxInputTokens: 256e3,
796
846
  default: true,
797
847
  supportedFileTypes: [],
@@ -805,6 +855,7 @@ const LLM_REGISTRY = {
805
855
  {
806
856
  name: "command-r-plus",
807
857
  displayName: "Command R+",
858
+ openrouterId: "cohere/command-r-plus-08-2024",
808
859
  maxInputTokens: 128e3,
809
860
  supportedFileTypes: [],
810
861
  pricing: {
@@ -817,6 +868,7 @@ const LLM_REGISTRY = {
817
868
  {
818
869
  name: "command-r",
819
870
  displayName: "Command R",
871
+ openrouterId: "cohere/command-r-08-2024",
820
872
  maxInputTokens: 128e3,
821
873
  supportedFileTypes: [],
822
874
  pricing: {
@@ -829,6 +881,7 @@ const LLM_REGISTRY = {
829
881
  {
830
882
  name: "command-r7b",
831
883
  displayName: "Command R7B",
884
+ openrouterId: "cohere/command-r7b-12-2024",
832
885
  maxInputTokens: 128e3,
833
886
  supportedFileTypes: [],
834
887
  pricing: {
@@ -840,8 +893,78 @@ const LLM_REGISTRY = {
840
893
  }
841
894
  ],
842
895
  baseURLSupport: "none",
843
- supportedFileTypes: []
896
+ supportedFileTypes: [],
844
897
  // Cohere currently doesn't support file uploads
898
+ openrouterPrefix: "cohere"
899
+ },
900
+ // https://platform.minimax.io/docs/api-reference/text-openai-api
901
+ // MiniMax provides an OpenAI-compatible endpoint at https://api.minimax.chat/v1
902
+ minimax: {
903
+ models: [
904
+ {
905
+ name: "MiniMax-M2.1",
906
+ displayName: "MiniMax M2.1",
907
+ openrouterId: "minimax/minimax-m2.1",
908
+ maxInputTokens: 196608,
909
+ default: true,
910
+ supportedFileTypes: []
911
+ },
912
+ {
913
+ name: "MiniMax-M2.1-lightning",
914
+ displayName: "MiniMax M2.1 Lightning",
915
+ openrouterId: "minimax/minimax-m2.1-lightning",
916
+ maxInputTokens: 196608,
917
+ supportedFileTypes: []
918
+ },
919
+ {
920
+ name: "MiniMax-M2",
921
+ displayName: "MiniMax M2",
922
+ openrouterId: "minimax/minimax-m2",
923
+ maxInputTokens: 2e5,
924
+ supportedFileTypes: []
925
+ },
926
+ {
927
+ name: "M2-her",
928
+ displayName: "MiniMax M2-Her",
929
+ openrouterId: "minimax/minimax-m2-her",
930
+ maxInputTokens: 32768,
931
+ supportedFileTypes: []
932
+ }
933
+ ],
934
+ baseURLSupport: "none",
935
+ supportedFileTypes: [],
936
+ openrouterPrefix: "minimax"
937
+ },
938
+ // https://docs.z.ai/api-reference/llm/chat-completion
939
+ // Zhipu AI GLM OpenAI-compatible endpoint: https://open.bigmodel.cn/api/paas/v4
940
+ glm: {
941
+ models: [
942
+ {
943
+ name: "glm-4.7",
944
+ displayName: "GLM 4.7",
945
+ openrouterId: "z-ai/glm-4.7",
946
+ maxInputTokens: 128e3,
947
+ default: true,
948
+ supportedFileTypes: []
949
+ },
950
+ {
951
+ name: "glm-4.7-flash",
952
+ displayName: "GLM 4.7 Flash",
953
+ openrouterId: "z-ai/glm-4.7-flash",
954
+ maxInputTokens: 128e3,
955
+ supportedFileTypes: []
956
+ },
957
+ {
958
+ name: "glm-4.7-flashx",
959
+ displayName: "GLM 4.7 FlashX",
960
+ openrouterId: "z-ai/glm-4.7-flashx",
961
+ maxInputTokens: 128e3,
962
+ supportedFileTypes: []
963
+ }
964
+ ],
965
+ baseURLSupport: "none",
966
+ supportedFileTypes: [],
967
+ openrouterPrefix: "z-ai"
845
968
  },
846
969
  // https://openrouter.ai/docs
847
970
  // OpenRouter is a unified API gateway providing access to 100+ models from various providers.
@@ -853,7 +976,9 @@ const LLM_REGISTRY = {
853
976
  // Fixed endpoint - baseURL auto-injected in resolver, no user override allowed
854
977
  supportedFileTypes: ["pdf", "image", "audio"],
855
978
  // Allow all types - user assumes responsibility for model capabilities
856
- supportsCustomModels: true
979
+ supportsCustomModels: true,
980
+ supportsAllRegistryModels: true
981
+ // Can serve models from all other providers
857
982
  },
858
983
  // https://docs.litellm.ai/
859
984
  // LiteLLM is an OpenAI-compatible proxy that unifies 100+ LLM providers.
@@ -1286,8 +1411,163 @@ const LLM_REGISTRY = {
1286
1411
  // Vision support depends on model
1287
1412
  supportsCustomModels: true
1288
1413
  // Accept any Ollama model name
1414
+ },
1415
+ // Dexto Gateway - OpenAI-compatible proxy through api.dexto.ai
1416
+ // Routes to OpenRouter with per-request billing (balance decrement)
1417
+ // Requires DEXTO_API_KEY from `dexto login`
1418
+ //
1419
+ // This is a first-class provider that users explicitly select.
1420
+ // Model IDs are in OpenRouter format (e.g., 'anthropic/claude-sonnet-4.5')
1421
+ dexto: {
1422
+ models: [
1423
+ // Claude models (Anthropic via OpenRouter)
1424
+ {
1425
+ name: "anthropic/claude-haiku-4.5",
1426
+ displayName: "Claude 4.5 Haiku",
1427
+ maxInputTokens: 2e5,
1428
+ default: true,
1429
+ supportedFileTypes: ["pdf", "image"],
1430
+ pricing: {
1431
+ inputPerM: 1,
1432
+ outputPerM: 5,
1433
+ cacheWritePerM: 1.25,
1434
+ cacheReadPerM: 0.1,
1435
+ currency: "USD",
1436
+ unit: "per_million_tokens"
1437
+ }
1438
+ },
1439
+ {
1440
+ name: "anthropic/claude-sonnet-4.5",
1441
+ displayName: "Claude 4.5 Sonnet",
1442
+ maxInputTokens: 2e5,
1443
+ supportedFileTypes: ["pdf", "image"],
1444
+ pricing: {
1445
+ inputPerM: 3,
1446
+ outputPerM: 15,
1447
+ cacheWritePerM: 3.75,
1448
+ cacheReadPerM: 0.3,
1449
+ currency: "USD",
1450
+ unit: "per_million_tokens"
1451
+ }
1452
+ },
1453
+ {
1454
+ name: "anthropic/claude-opus-4.5",
1455
+ displayName: "Claude 4.5 Opus",
1456
+ maxInputTokens: 2e5,
1457
+ supportedFileTypes: ["pdf", "image"],
1458
+ pricing: {
1459
+ inputPerM: 5,
1460
+ outputPerM: 25,
1461
+ cacheWritePerM: 6.25,
1462
+ cacheReadPerM: 0.5,
1463
+ currency: "USD",
1464
+ unit: "per_million_tokens"
1465
+ }
1466
+ },
1467
+ // OpenAI models (via OpenRouter)
1468
+ {
1469
+ name: "openai/gpt-5.2",
1470
+ displayName: "GPT-5.2",
1471
+ maxInputTokens: 4e5,
1472
+ supportedFileTypes: ["pdf", "image"],
1473
+ pricing: {
1474
+ inputPerM: 1.75,
1475
+ outputPerM: 14,
1476
+ cacheReadPerM: 0.175,
1477
+ currency: "USD",
1478
+ unit: "per_million_tokens"
1479
+ }
1480
+ },
1481
+ {
1482
+ name: "openai/gpt-5.2-codex",
1483
+ displayName: "GPT-5.2 Codex",
1484
+ maxInputTokens: 4e5,
1485
+ supportedFileTypes: ["pdf", "image"],
1486
+ pricing: {
1487
+ inputPerM: 1.75,
1488
+ outputPerM: 14,
1489
+ cacheReadPerM: 0.175,
1490
+ currency: "USD",
1491
+ unit: "per_million_tokens"
1492
+ }
1493
+ },
1494
+ // Google models (via OpenRouter)
1495
+ {
1496
+ name: "google/gemini-3-pro-preview",
1497
+ displayName: "Gemini 3 Pro",
1498
+ maxInputTokens: 1048576,
1499
+ supportedFileTypes: ["pdf", "image", "audio"],
1500
+ pricing: {
1501
+ inputPerM: 2,
1502
+ outputPerM: 12,
1503
+ cacheReadPerM: 0.2,
1504
+ currency: "USD",
1505
+ unit: "per_million_tokens"
1506
+ }
1507
+ },
1508
+ {
1509
+ name: "google/gemini-3-flash-preview",
1510
+ displayName: "Gemini 3 Flash",
1511
+ maxInputTokens: 1048576,
1512
+ supportedFileTypes: ["pdf", "image", "audio"],
1513
+ pricing: {
1514
+ inputPerM: 0.5,
1515
+ outputPerM: 3,
1516
+ cacheReadPerM: 0.05,
1517
+ currency: "USD",
1518
+ unit: "per_million_tokens"
1519
+ }
1520
+ },
1521
+ // Free models (via OpenRouter)
1522
+ {
1523
+ name: "qwen/qwen3-coder:free",
1524
+ displayName: "Qwen3 Coder (Free)",
1525
+ maxInputTokens: 262e3,
1526
+ supportedFileTypes: []
1527
+ // Free - no pricing
1528
+ },
1529
+ {
1530
+ name: "deepseek/deepseek-r1-0528:free",
1531
+ displayName: "DeepSeek R1 (Free)",
1532
+ maxInputTokens: 163840,
1533
+ supportedFileTypes: []
1534
+ // Free - no pricing
1535
+ },
1536
+ // Other models (via OpenRouter)
1537
+ {
1538
+ name: "z-ai/glm-4.7",
1539
+ displayName: "GLM 4.7",
1540
+ maxInputTokens: 202752,
1541
+ supportedFileTypes: [],
1542
+ pricing: {
1543
+ inputPerM: 0.4,
1544
+ outputPerM: 1.5,
1545
+ currency: "USD",
1546
+ unit: "per_million_tokens"
1547
+ }
1548
+ },
1549
+ {
1550
+ name: "minimax/minimax-m2.1",
1551
+ displayName: "Minimax M2.1",
1552
+ maxInputTokens: 196608,
1553
+ supportedFileTypes: [],
1554
+ pricing: {
1555
+ inputPerM: 0.27,
1556
+ outputPerM: 1.1,
1557
+ currency: "USD",
1558
+ unit: "per_million_tokens"
1559
+ }
1560
+ }
1561
+ ],
1562
+ baseURLSupport: "none",
1563
+ // Fixed endpoint: https://api.dexto.ai/v1
1564
+ supportedFileTypes: ["pdf", "image", "audio"],
1565
+ // Same as OpenRouter
1566
+ supportsCustomModels: true,
1567
+ // Accept any OpenRouter model ID beyond the preset list
1568
+ supportsAllRegistryModels: true
1569
+ // Can serve models from all other providers via OpenRouter
1289
1570
  }
1290
- // TODO: Add 'dexto' provider (similar to openrouter, uses https://api.dexto.ai/v1)
1291
1571
  };
1292
1572
  function stripBedrockRegionPrefix(model) {
1293
1573
  if (model.startsWith("eu.") || model.startsWith("us.")) {
@@ -1310,17 +1590,20 @@ function getSupportedModels(provider) {
1310
1590
  return providerInfo.models.map((m) => m.name);
1311
1591
  }
1312
1592
  function getMaxInputTokensForModel(provider, model, logger) {
1313
- const providerInfo = LLM_REGISTRY[provider];
1314
- const normalizedModel = stripBedrockRegionPrefix(model).toLowerCase();
1593
+ const resolved = resolveToNativeProvider(provider, model);
1594
+ const providerInfo = LLM_REGISTRY[resolved.provider];
1595
+ const normalizedModel = stripBedrockRegionPrefix(resolved.model).toLowerCase();
1315
1596
  const modelInfo = providerInfo.models.find((m) => m.name.toLowerCase() === normalizedModel);
1316
1597
  if (!modelInfo) {
1317
- const supportedModels = getSupportedModels(provider).join(", ");
1598
+ const supportedModels = getSupportedModels(resolved.provider).join(", ");
1318
1599
  logger?.error(
1319
- `Model '${model}' not found for provider '${provider}' in LLM registry. Supported models: ${supportedModels}`
1600
+ `Model '${resolved.model}' not found for provider '${resolved.provider}' in LLM registry. Supported models: ${supportedModels}`
1320
1601
  );
1321
- throw LLMError.unknownModel(provider, model);
1602
+ throw LLMError.unknownModel(resolved.provider, resolved.model);
1322
1603
  }
1323
- logger?.debug(`Found max tokens for ${provider}/${model}: ${modelInfo.maxInputTokens}`);
1604
+ logger?.debug(
1605
+ `Found max tokens for ${resolved.provider}/${resolved.model}: ${modelInfo.maxInputTokens}`
1606
+ );
1324
1607
  return modelInfo.maxInputTokens;
1325
1608
  }
1326
1609
  function isValidProviderModel(provider, model) {
@@ -1329,6 +1612,27 @@ function isValidProviderModel(provider, model) {
1329
1612
  return providerInfo.models.some((m) => m.name.toLowerCase() === normalizedModel);
1330
1613
  }
1331
1614
  function getProviderFromModel(model) {
1615
+ if (model.includes("/")) {
1616
+ const [prefix, ...rest] = model.split("/");
1617
+ const modelName = rest.join("/");
1618
+ if (prefix) {
1619
+ const normalizedPrefix = prefix.toLowerCase();
1620
+ for (const provider of LLM_PROVIDERS) {
1621
+ const providerPrefix = getOpenrouterPrefix(provider);
1622
+ if (providerPrefix?.toLowerCase() === normalizedPrefix) {
1623
+ const providerInfo = LLM_REGISTRY[provider];
1624
+ const normalizedModelName = stripBedrockRegionPrefix(modelName).toLowerCase();
1625
+ const existsInProvider = providerInfo.models.some(
1626
+ (m) => m.name.toLowerCase() === normalizedModelName || m.openrouterId?.toLowerCase() === model.toLowerCase()
1627
+ );
1628
+ if (existsInProvider) {
1629
+ return provider;
1630
+ }
1631
+ break;
1632
+ }
1633
+ }
1634
+ }
1635
+ }
1332
1636
  const normalizedModel = stripBedrockRegionPrefix(model).toLowerCase();
1333
1637
  for (const provider of LLM_PROVIDERS) {
1334
1638
  const info = LLM_REGISTRY[provider];
@@ -1357,6 +1661,133 @@ function supportsCustomModels(provider) {
1357
1661
  const providerInfo = LLM_REGISTRY[provider];
1358
1662
  return providerInfo.supportsCustomModels === true;
1359
1663
  }
1664
+ function hasAllRegistryModelsSupport(provider) {
1665
+ const providerInfo = LLM_REGISTRY[provider];
1666
+ return providerInfo.supportsAllRegistryModels === true;
1667
+ }
1668
+ function getOpenrouterPrefix(provider) {
1669
+ return LLM_REGISTRY[provider].openrouterPrefix;
1670
+ }
1671
+ const GATEWAY_ACCESSIBLE_PROVIDERS = Object.entries(LLM_REGISTRY).filter(
1672
+ ([provider, info]) => (
1673
+ // Has openrouterPrefix (needs transformation)
1674
+ info.openrouterPrefix !== void 0 || // Special case: groq models already have vendor prefixes, no transformation needed
1675
+ provider === "groq"
1676
+ )
1677
+ ).map(([provider]) => provider);
1678
+ function getAllModelsForProvider(provider) {
1679
+ const providerInfo = LLM_REGISTRY[provider];
1680
+ if (!providerInfo.supportsAllRegistryModels) {
1681
+ return providerInfo.models.map((m) => ({ ...m }));
1682
+ }
1683
+ const allModels = [];
1684
+ for (const model of providerInfo.models) {
1685
+ allModels.push({ ...model, originalProvider: provider });
1686
+ }
1687
+ for (const sourceProvider of GATEWAY_ACCESSIBLE_PROVIDERS) {
1688
+ const sourceInfo = LLM_REGISTRY[sourceProvider];
1689
+ for (const model of sourceInfo.models) {
1690
+ allModels.push({
1691
+ ...model,
1692
+ originalProvider: sourceProvider
1693
+ });
1694
+ }
1695
+ }
1696
+ return allModels;
1697
+ }
1698
+ function transformModelNameForProvider(model, originalProvider, targetProvider) {
1699
+ if (!hasAllRegistryModelsSupport(targetProvider)) {
1700
+ return model;
1701
+ }
1702
+ if (hasAllRegistryModelsSupport(originalProvider)) {
1703
+ return model;
1704
+ }
1705
+ if (model.includes("/")) {
1706
+ return model;
1707
+ }
1708
+ const prefix = getOpenrouterPrefix(originalProvider);
1709
+ if (!prefix) {
1710
+ return model;
1711
+ }
1712
+ const providerInfo = LLM_REGISTRY[originalProvider];
1713
+ if (providerInfo) {
1714
+ const normalizedModel = model.toLowerCase();
1715
+ const modelInfo = providerInfo.models.find((m) => m.name.toLowerCase() === normalizedModel);
1716
+ if (modelInfo?.openrouterId) {
1717
+ return modelInfo.openrouterId;
1718
+ }
1719
+ }
1720
+ throw new DextoRuntimeError(
1721
+ LLMErrorCode.MODEL_UNKNOWN,
1722
+ ErrorScope.LLM,
1723
+ ErrorType.SYSTEM,
1724
+ `Model '${model}' from provider '${originalProvider}' has no openrouterId mapping. All models that can be used via gateway providers must have explicit openrouterId in the registry.`,
1725
+ { model, originalProvider, targetProvider }
1726
+ );
1727
+ }
1728
+ function resolveModelOrigin(model, gatewayProvider) {
1729
+ if (!hasAllRegistryModelsSupport(gatewayProvider)) {
1730
+ return { provider: gatewayProvider, model };
1731
+ }
1732
+ if (model.includes("/")) {
1733
+ const [prefix, ...rest] = model.split("/");
1734
+ const modelName = rest.join("/");
1735
+ if (prefix) {
1736
+ const normalizedPrefix = prefix.toLowerCase();
1737
+ for (const provider of LLM_PROVIDERS) {
1738
+ const providerPrefix = getOpenrouterPrefix(provider);
1739
+ if (providerPrefix?.toLowerCase() === normalizedPrefix) {
1740
+ const providerInfo = LLM_REGISTRY[provider];
1741
+ const nativeModel = providerInfo?.models.find(
1742
+ (m) => m.openrouterId?.toLowerCase() === model.toLowerCase()
1743
+ );
1744
+ if (nativeModel) {
1745
+ return { provider, model: nativeModel.name };
1746
+ }
1747
+ return { provider, model: modelName };
1748
+ }
1749
+ }
1750
+ }
1751
+ for (const sourceProvider of GATEWAY_ACCESSIBLE_PROVIDERS) {
1752
+ const sourceInfo = LLM_REGISTRY[sourceProvider];
1753
+ if (sourceInfo.models.some((m) => m.name.toLowerCase() === model.toLowerCase())) {
1754
+ return { provider: sourceProvider, model };
1755
+ }
1756
+ }
1757
+ }
1758
+ for (const sourceProvider of GATEWAY_ACCESSIBLE_PROVIDERS) {
1759
+ const sourceInfo = LLM_REGISTRY[sourceProvider];
1760
+ const normalizedModel = stripBedrockRegionPrefix(model).toLowerCase();
1761
+ if (sourceInfo.models.some((m) => m.name.toLowerCase() === normalizedModel)) {
1762
+ return { provider: sourceProvider, model };
1763
+ }
1764
+ }
1765
+ return null;
1766
+ }
1767
+ function resolveToNativeProvider(provider, model) {
1768
+ if (hasAllRegistryModelsSupport(provider)) {
1769
+ const origin = resolveModelOrigin(model, provider);
1770
+ if (origin) {
1771
+ return origin;
1772
+ }
1773
+ }
1774
+ return { provider, model };
1775
+ }
1776
+ function isModelValidForProvider(provider, model) {
1777
+ const providerInfo = LLM_REGISTRY[provider];
1778
+ const normalizedModel = stripBedrockRegionPrefix(model).toLowerCase();
1779
+ if (providerInfo.models.some((m) => m.name.toLowerCase() === normalizedModel)) {
1780
+ return true;
1781
+ }
1782
+ if (providerInfo.supportsCustomModels) {
1783
+ return true;
1784
+ }
1785
+ if (providerInfo.supportsAllRegistryModels) {
1786
+ const origin = resolveModelOrigin(model, provider);
1787
+ return origin !== null;
1788
+ }
1789
+ return false;
1790
+ }
1360
1791
  const API_KEY_OPTIONAL_PROVIDERS = /* @__PURE__ */ new Set([
1361
1792
  "local",
1362
1793
  // Native node-llama-cpp execution - no auth needed
@@ -1375,14 +1806,15 @@ function requiresApiKey(provider) {
1375
1806
  return !API_KEY_OPTIONAL_PROVIDERS.has(provider);
1376
1807
  }
1377
1808
  function getSupportedFileTypesForModel(provider, model) {
1378
- const providerInfo = LLM_REGISTRY[provider];
1379
- if (acceptsAnyModel(provider)) {
1809
+ const resolved = resolveToNativeProvider(provider, model);
1810
+ const providerInfo = LLM_REGISTRY[resolved.provider];
1811
+ if (acceptsAnyModel(resolved.provider)) {
1380
1812
  return providerInfo.supportedFileTypes;
1381
1813
  }
1382
- const normalizedModel = stripBedrockRegionPrefix(model).toLowerCase();
1814
+ const normalizedModel = stripBedrockRegionPrefix(resolved.model).toLowerCase();
1383
1815
  const modelInfo = providerInfo.models.find((m) => m.name.toLowerCase() === normalizedModel);
1384
1816
  if (!modelInfo) {
1385
- throw LLMError.unknownModel(provider, model);
1817
+ throw LLMError.unknownModel(resolved.provider, resolved.model);
1386
1818
  }
1387
1819
  return modelInfo.supportedFileTypes;
1388
1820
  }
@@ -1513,26 +1945,28 @@ function getEffectiveMaxInputTokens(config, logger) {
1513
1945
  }
1514
1946
  }
1515
1947
  function getModelPricing(provider, model) {
1516
- const providerInfo = LLM_REGISTRY[provider];
1517
- if (acceptsAnyModel(provider)) {
1948
+ const resolved = resolveToNativeProvider(provider, model);
1949
+ const providerInfo = LLM_REGISTRY[resolved.provider];
1950
+ if (acceptsAnyModel(resolved.provider)) {
1518
1951
  return void 0;
1519
1952
  }
1520
- const normalizedModel = stripBedrockRegionPrefix(model).toLowerCase();
1953
+ const normalizedModel = stripBedrockRegionPrefix(resolved.model).toLowerCase();
1521
1954
  const modelInfo = providerInfo.models.find((m) => m.name.toLowerCase() === normalizedModel);
1522
1955
  return modelInfo?.pricing;
1523
1956
  }
1524
1957
  function getModelDisplayName(model, provider) {
1525
- let resolvedProvider;
1958
+ let inferredProvider;
1526
1959
  try {
1527
- resolvedProvider = provider ?? getProviderFromModel(model);
1960
+ inferredProvider = provider ?? getProviderFromModel(model);
1528
1961
  } catch {
1529
1962
  return model;
1530
1963
  }
1531
- const providerInfo = LLM_REGISTRY[resolvedProvider];
1532
- if (!providerInfo || acceptsAnyModel(resolvedProvider)) {
1964
+ const resolved = resolveToNativeProvider(inferredProvider, model);
1965
+ const providerInfo = LLM_REGISTRY[resolved.provider];
1966
+ if (!providerInfo || acceptsAnyModel(resolved.provider)) {
1533
1967
  return model;
1534
1968
  }
1535
- const normalizedModel = stripBedrockRegionPrefix(model).toLowerCase();
1969
+ const normalizedModel = stripBedrockRegionPrefix(resolved.model).toLowerCase();
1536
1970
  const modelInfo = providerInfo.models.find((m) => m.name.toLowerCase() === normalizedModel);
1537
1971
  return modelInfo?.displayName ?? model;
1538
1972
  }
@@ -1563,6 +1997,7 @@ export {
1563
1997
  MIME_TYPE_TO_FILE_TYPE,
1564
1998
  acceptsAnyModel,
1565
1999
  calculateCost,
2000
+ getAllModelsForProvider,
1566
2001
  getAllSupportedModels,
1567
2002
  getAllowedMimeTypes,
1568
2003
  getDefaultModelForProvider,
@@ -1574,13 +2009,17 @@ export {
1574
2009
  getSupportedFileTypesForModel,
1575
2010
  getSupportedModels,
1576
2011
  getSupportedProviders,
2012
+ hasAllRegistryModelsSupport,
2013
+ isModelValidForProvider,
1577
2014
  isReasoningCapableModel,
1578
2015
  isValidProviderModel,
1579
2016
  modelSupportsFileType,
1580
2017
  requiresApiKey,
1581
2018
  requiresBaseURL,
2019
+ resolveModelOrigin,
1582
2020
  stripBedrockRegionPrefix,
1583
2021
  supportsBaseURL,
1584
2022
  supportsCustomModels,
2023
+ transformModelNameForProvider,
1585
2024
  validateModelFileSupport
1586
2025
  };