@plurnk/plurnk-providers 1.7.0 → 1.8.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 (88) hide show
  1. package/.env.defaults +25 -13
  2. package/README.md +8 -1
  3. package/SPEC.md +93 -15
  4. package/dist/AiSdkProvider.d.ts +6 -3
  5. package/dist/AiSdkProvider.d.ts.map +1 -1
  6. package/dist/AiSdkProvider.js +108 -51
  7. package/dist/AiSdkProvider.js.map +1 -1
  8. package/dist/Mock.d.ts +1 -0
  9. package/dist/Mock.d.ts.map +1 -1
  10. package/dist/Mock.js +2 -0
  11. package/dist/Mock.js.map +1 -1
  12. package/dist/Pool.d.ts +2 -0
  13. package/dist/Pool.d.ts.map +1 -1
  14. package/dist/Pool.js +3 -0
  15. package/dist/Pool.js.map +1 -1
  16. package/dist/ProviderRegistry.d.ts.map +1 -1
  17. package/dist/ProviderRegistry.js +11 -10
  18. package/dist/ProviderRegistry.js.map +1 -1
  19. package/dist/accounting.d.ts.map +1 -1
  20. package/dist/accounting.js +7 -6
  21. package/dist/accounting.js.map +1 -1
  22. package/dist/aiSdkTransport.d.ts +2 -1
  23. package/dist/aiSdkTransport.d.ts.map +1 -1
  24. package/dist/aiSdkTransport.js +29 -6
  25. package/dist/aiSdkTransport.js.map +1 -1
  26. package/dist/catalogProvider.d.ts +4 -1
  27. package/dist/catalogProvider.d.ts.map +1 -1
  28. package/dist/catalogProvider.js +94 -3
  29. package/dist/catalogProvider.js.map +1 -1
  30. package/dist/compatibleProvider.d.ts.map +1 -1
  31. package/dist/compatibleProvider.js +2 -0
  32. package/dist/compatibleProvider.js.map +1 -1
  33. package/dist/cost.d.ts.map +1 -1
  34. package/dist/cost.js +5 -4
  35. package/dist/cost.js.map +1 -1
  36. package/dist/discover.d.ts +2 -0
  37. package/dist/discover.d.ts.map +1 -1
  38. package/dist/discover.js +13 -2
  39. package/dist/discover.js.map +1 -1
  40. package/dist/env.d.ts +3 -2
  41. package/dist/env.d.ts.map +1 -1
  42. package/dist/env.js +11 -4
  43. package/dist/env.js.map +1 -1
  44. package/dist/index.d.ts +9 -5
  45. package/dist/index.d.ts.map +1 -1
  46. package/dist/index.js +6 -3
  47. package/dist/index.js.map +1 -1
  48. package/dist/notices.d.ts +1 -1
  49. package/dist/notices.d.ts.map +1 -1
  50. package/dist/openai.d.ts +1 -1
  51. package/dist/openai.d.ts.map +1 -1
  52. package/dist/openai.js +1 -1
  53. package/dist/openai.js.map +1 -1
  54. package/dist/sdkModels.d.ts +2 -0
  55. package/dist/sdkModels.d.ts.map +1 -1
  56. package/dist/sdkModels.js +163 -19
  57. package/dist/sdkModels.js.map +1 -1
  58. package/dist/types.d.ts +8 -2
  59. package/dist/types.d.ts.map +1 -1
  60. package/dist/types.js +10 -1
  61. package/dist/types.js.map +1 -1
  62. package/package.json +9 -9
  63. package/src/AiSdkProvider.test.ts +206 -32
  64. package/src/AiSdkProvider.ts +140 -54
  65. package/src/Mock.ts +2 -0
  66. package/src/Pool.test.ts +1 -0
  67. package/src/Pool.ts +5 -0
  68. package/src/ProviderRegistry.test.ts +27 -14
  69. package/src/ProviderRegistry.ts +19 -10
  70. package/src/accounting.test.ts +6 -2
  71. package/src/accounting.ts +7 -6
  72. package/src/aiSdkTransport.ts +32 -7
  73. package/src/catalogProvider.test.ts +151 -19
  74. package/src/catalogProvider.ts +125 -3
  75. package/src/compatibleProvider.test.ts +13 -10
  76. package/src/compatibleProvider.ts +2 -0
  77. package/src/cost.ts +5 -4
  78. package/src/discover.test.ts +27 -0
  79. package/src/discover.ts +20 -3
  80. package/src/env.test.ts +23 -8
  81. package/src/env.ts +17 -8
  82. package/src/index.ts +16 -8
  83. package/src/notices.ts +1 -1
  84. package/src/openai.ts +1 -1
  85. package/src/providerDefaults.test.ts +50 -0
  86. package/src/sdkModels.test.ts +142 -8
  87. package/src/sdkModels.ts +201 -19
  88. package/src/types.ts +16 -0
package/.env.defaults CHANGED
@@ -2,7 +2,8 @@
2
2
  # PLURNK_PROVIDERS_* knobs and provider declarations ({§operator-config-env-defaults});
3
3
  # every package owns what it reads, and this file IS the configuration reference.
4
4
  # The daemon assembles every installed member's file into one floor (set-if-unset under the
5
- # operator's env) - do NOT edit this file; put YOUR config in ~/.plurnk/.env or ./.env. A key
5
+ # operator's env) - do NOT edit this file; put YOUR config in
6
+ # $XDG_CONFIG_HOME/plurnk/.env or ./.env. A key
6
7
  # claimed by two packages crashes boot naming both.
7
8
  #
8
9
  # EVERY PLURNK_PROVIDERS_* knob is per-alias-scopable: PLURNK_PROVIDERS_<KNOB>_<alias> wins over
@@ -13,6 +14,13 @@
13
14
  # and model facts. {§model-fact-resolution} defines precedence per fact; there is
14
15
  # no live price fetch. Secret VALUES never belong here.
15
16
 
17
+ # --- OpenRouter application attribution ({§openrouter-app-attribution}) ---
18
+ # OpenRouter uses the public URL as the app identity and the title for display.
19
+ # Override both for a downstream application. An explicitly empty URL suppresses
20
+ # attribution entirely; a title without a URL is never sent.
21
+ OPENROUTER_HTTP_REFERER=https://github.com/plurnk/plurnk-service
22
+ OPENROUTER_APP_TITLE=Plurnk
23
+
16
24
  # --- Generation envelope ({§provider-generation-envelope}, #242) ---
17
25
  # OUTPUT_BUDGET is one total response ceiling, including hidden reasoning. It accepts a
18
26
  # percentage of the effective context window or an absolute token count and is always
@@ -21,12 +29,10 @@
21
29
  PLURNK_PROVIDERS_OUTPUT_BUDGET=35%
22
30
  # PLURNK_PROVIDERS_REASONING_BUDGET=8192
23
31
 
24
- # --- Side-channel reasoning (SPEC §4, #32/#33/#399) ---
25
- # ACTIVATION and BUDGET are separate so a numeric can never silently flip wire flags.
26
- # off | adaptive | on. The provider maps intent to each backend's native mechanism
27
- # (reasoning_effort, enable_thinking, think, ...). Default ADAPTIVE (#399):
28
- # defer activation and depth to the backend's documented default. Use an alias-scoped
29
- # ON when a reasoning-capable model defaults off and the operator wants it enabled.
32
+ # --- Side-channel reasoning ({§provider-reasoning-policy}) ---
33
+ # off | adaptive | low | medium | high. Policy and budget remain independent;
34
+ # adaptive requests native dynamic reasoning where available and otherwise the
35
+ # provider's supported high posture. Alias-scoped values seed a worker once.
30
36
  PLURNK_PROVIDERS_REASONING=adaptive
31
37
 
32
38
  # Response-content interpretation ({§provider-tagged-reasoning}) is independent
@@ -42,7 +48,8 @@ PLURNK_PROVIDERS_REASONING_RESPONSE_STYLE=verbatim
42
48
  # the floor the provider manages wherever a grammar rides (greedy-under-mask loops without it).
43
49
  PLURNK_PROVIDERS_TEMPERATURE=0.2
44
50
  PLURNK_PROVIDERS_REPEAT_PENALTY=1.15
45
- # FREQUENCY_PENALTY (#426): optional cloud anti-degeneration tuning. API acceptance
51
+ # FREQUENCY_PENALTY (https://github.com/plurnk/plurnk-service/issues/426):
52
+ # optional cloud anti-degeneration tuning. API acceptance
46
53
  # permits the field to ride but does not establish its semantic effect, and provider
47
54
  # implementations differ. The portable floor is off; enable per alias only from
48
55
  # provider documentation or a controlled behavioral experiment.
@@ -59,7 +66,8 @@ PLURNK_PROVIDERS_CACHE_AFFINITY=1
59
66
  # stable-system marks only the reusable system boundary on supported Claude
60
67
  # routes; off requests no explicit cache write. Provider-default lifetime is 5m.
61
68
  PLURNK_PROVIDERS_CACHE_WRITE_POLICY=stable-system
62
- # #567: DRY is a llama.cpp-only repeated-sequence penalty. It can reduce
69
+ # https://github.com/plurnk/plurnk-service/issues/567: DRY is a llama.cpp-only
70
+ # repeated-sequence penalty. It can reduce
63
71
  # degenerate loops, but it can also corrupt exact source, identifiers, quoted
64
72
  # evidence, and other repetition required by PLURNK operations. The portable
65
73
  # server-wide default is off. A nonzero alias override is an explicit fidelity
@@ -140,8 +148,9 @@ PLURNK_PROVIDERS_PROBE_DELAY=250
140
148
  # an endpoint Models.dev does not list. NAME is the alias provider segment.
141
149
  # PLURNK_PROVIDERS_PROVIDER_<NAME>_NPM=<supported AI SDK package>
142
150
  # PLURNK_PROVIDERS_PROVIDER_<NAME>_BASE_URL=<endpoint>
143
- # PLURNK_PROVIDERS_PROVIDER_<NAME>_API_KEY_ENV=<comma-separated env names>
144
- PLURNK_PROVIDERS_PROVIDER_CLOUDFLARE_API_KEY_ENV=CLOUDFLARE_API_TOKEN,CLOUDFLARE_API_KEY
151
+ # PLURNK_PROVIDERS_PROVIDER_<NAME>_API_KEY_ENV=<one exact env name>
152
+ # Models.dev is authoritative for cataloged providers ({§provider-fact-authority}):
153
+ # package defaults never redefine a cataloged NPM, BASE_URL, or credential name.
145
154
  # Fireworks reasoners default on when reasoning_effort is omitted; explicit
146
155
  # "none" is its off switch. This is a declared wire exception, not a registry.
147
156
  PLURNK_PROVIDERS_PROVIDER_FIREWORKS_REASONING_STYLE=effort_explicit
@@ -157,13 +166,16 @@ PLURNK_PROVIDERS_PROVIDER_QIANFAN_NPM=@ai-sdk/openai-compatible
157
166
  PLURNK_PROVIDERS_PROVIDER_QIANFAN_BASE_URL=https://qianfan.baidubce.com/v2
158
167
  PLURNK_PROVIDERS_PROVIDER_QIANFAN_API_KEY_ENV=QIANFAN_API_KEY
159
168
 
160
- # --- Alias cascade (SPEC §5) - declare aliases, then pick the active one ---
169
+ # --- Model selectors and optional alias cascade (SPEC §5) ---
161
170
  # First path segment is the provider name; the rest is the provider-native model id (may
162
- # contain "/"). Operator-specific, no default - the examples are commented.
171
+ # contain "/"). PLURNK_MODEL accepts that exact route or a declared alias. An
172
+ # alias is useful when the route needs a reusable name, endpoint, or scoped tuning.
173
+ # Operator-specific, no default - the examples are commented.
163
174
  # PLURNK_MODEL_gemma=openai/macher.gguf
164
175
  # PLURNK_MODEL_opus=anthropic/claude-opus-4-8
165
176
  # PLURNK_MODEL_sonnet=openrouter/anthropic/claude-sonnet-latest
166
177
  # PLURNK_MODEL=gemma
178
+ # PLURNK_MODEL=google/gemini-3-flash
167
179
  #
168
180
  # PLURNK_BASEURL_<alias> - bind an endpoint to ONE alias (the only way to run N self-hosted
169
181
  # boxes of one provider: openai=llama.cpp/vLLM, ollama). WINS over the provider's *_BASE_URL;
package/README.md CHANGED
@@ -40,7 +40,14 @@ discovery and environment-file defaults.
40
40
 
41
41
  ## Configure a model
42
42
 
43
- Declare an alias, then select it:
43
+ Select a catalog route directly:
44
+
45
+ ```dotenv
46
+ PLURNK_MODEL=google/gemini-3-flash
47
+ GEMINI_API_KEY=...
48
+ ```
49
+
50
+ Declare an alias when the route needs a reusable name or scoped tuning:
44
51
 
45
52
  ```dotenv
46
53
  PLURNK_MODEL_fast=openai/gpt-5-mini
package/SPEC.md CHANGED
@@ -69,7 +69,7 @@ interface Provider {
69
69
  `contextWindow` is the effective total context envelope resolved under
70
70
  {§model-fact-resolution}: the minimum of known model capacity and any stricter
71
71
  operator cap. `null` means genuinely unknown; a consumer MUST NOT invent a
72
- stand-in. The context-window knob is a hard cap, never model-facing grinder
72
+ stand-in. The context-window knob is a hard cap, never a model-facing curation
73
73
  pressure.
74
74
 
75
75
  §provider-prompt-measurement `PromptTokenMeasurement` is a discriminated
@@ -218,21 +218,51 @@ PLURNK maps its generic settings to AI SDK call settings:
218
218
  - presence and frequency penalties;
219
219
  - stop sequences and seed;
220
220
  - output-token ceiling;
221
- - `off`, provider-default `adaptive`, or explicit `on` reasoning intent, with
222
- an optional operator budget.
221
+ - `off`, `adaptive`, or fixed `low`, `medium`, or `high` reasoning policy, with
222
+ an independent optional operator budget.
223
223
 
224
224
  Provider-specific options are permitted only where they preserve a documented
225
225
  PLURNK product contract the generic SDK surface cannot express.
226
226
 
227
+ §provider-reasoning-policy The portable vocabulary comes from
228
+ {§reasoning-policy-wire}. `adaptive` requests the provider's
229
+ documented dynamic mechanism where one exists and otherwise requests its
230
+ supported `high` posture; it is affirmative, not an omission that may silently
231
+ disable reasoning. A fixed policy retains its named intent and is rejected
232
+ before provider I/O when the selected adapter cannot represent it without
233
+ coercion. Every provider exposes its exact supported subset. A numeric reasoning
234
+ budget constrains the generation envelope independently and never selects or
235
+ changes policy.
236
+
237
+ The catalog adapter derives the exposed subset from the selected model and the
238
+ installed native SDK contract:
239
+
240
+ | Route | `adaptive` projection | Advertised subset on a reasoning model |
241
+ | --- | --- | --- |
242
+ | Anthropic or Bedrock model with native adaptive `thinking` | Native adaptive `thinking`, without a fixed effort | `off`, `adaptive`, `low`, `medium`, `high` |
243
+ | Anthropic or Bedrock model with manual `thinking` | A `high` manual allowance inside the total output envelope | `off`, `adaptive`, `low`, `medium`, `high` |
244
+ | Gemini 2.5 | Dynamic `thinkingBudget` | All five, except Pro omits unsupported `off` |
245
+ | Gemini 3+ | Native `thinkingLevel: "high"` | `adaptive`, `low`, `medium`, `high`; its mandatory minimum is not mislabeled `off` |
246
+ | xAI graded model | Native `high` | All five, except Grok 4.6 omits unsupported `off` |
247
+ | xAI fixed-reasoning model | Documented model default | `adaptive` |
248
+ | Mistral model with adjustable effort | Native `high` | `off`, `adaptive`, `high`; SDK coercions of low/medium are not exposed |
249
+ | Mistral reasoning model without adjustable SDK effort | Documented model default | `adaptive` |
250
+ | Other native graded adapter | Native `high` | `off`, `adaptive`, `low`, `medium`, `high` |
251
+ | Activation-only compatible adapter | Explicit activation or documented reasoning default | `off`, `adaptive` |
252
+
253
+ Models.dev's reasoning bit selects no row by itself: it identifies capability,
254
+ while the installed adapter and selected model determine representable policy.
255
+
227
256
  §provider-readable-reasoning When the effective reasoning posture is not
228
257
  `off`, a native adapter MUST request readable reasoning summaries if its
229
258
  provider requires a separate response-visibility option. That option neither
230
259
  activates reasoning nor selects its depth. The exact wire projection belongs to
231
260
  the provider adapter; Models.dev's reasoning bit remains capability metadata.
232
261
 
233
- The portable SDK surface has no boolean-enabled reasoning value. An unqualified
234
- `on` therefore projects to its conventional `medium` enabled posture. This is a
235
- wire activation value, not a reasoning budget or output-token ceiling.
262
+ §provider-sdk-warning AI SDK compatibility, unsupported-feature, deprecation,
263
+ and other call warnings become source-attributed provider Notices on the
264
+ successful exchange. A lossy adapter projection is therefore observable rather
265
+ than disappearing in transport internals.
236
266
 
237
267
  §provider-cache-affinity **Cache affinity is route-owned request projection.**
238
268
  When a provider documents a semantics-preserving conversation, session, or
@@ -257,9 +287,11 @@ reasoning intent to its OpenAI-compatible controls:
257
287
  | PLURNK posture | `thinking` | `reasoning_effort` |
258
288
  | --------------- | --------------------- | -------------------- |
259
289
  | `off` | `{ type: disabled }` | omitted |
260
- | `adaptive` | omitted | omitted |
261
- | `on` | `{ type: enabled }` | omitted |
262
- | `on` + budget | `{ type: enabled }` | budget-derived tier |
290
+ | `adaptive` | `{ type: enabled }` | omitted |
291
+ | `high` | `{ type: enabled }` | `high` |
292
+
293
+ The direct API does not distinguish portable `low` or `medium` intent and
294
+ therefore advertises only `off`, `adaptive`, and `high`.
263
295
 
264
296
  The compatible transport is deliberately retained for:
265
297
 
@@ -302,9 +334,23 @@ defaults.
302
334
 
303
335
  §provider-resolution `PLURNK_MODEL_<alias>=<provider>/<model-id>` declares an
304
336
  alias.
305
- `PLURNK_MODEL=<alias>` selects the boot alias. Model IDs may contain `/`.
337
+ `PLURNK_MODEL=<selector>` selects either a declared alias or an exact
338
+ `<provider>/<model-id>` route. Model IDs may contain `/`; only the first slash
339
+ separates provider from model. Exact routes carry no fabricated alias and use
340
+ the global provider configuration. Declared aliases retain their provenance,
341
+ endpoint override, and alias-scoped tuning.
306
342
  `PLURNK_BASEURL_<alias>` is a per-alias endpoint override.
307
343
 
344
+ §model-catalog-readiness **Catalog readiness and construction share one local
345
+ configuration predicate.** For each Models.dev provider, readiness evaluates
346
+ the same effective credential names, endpoint template coordinates, base-URL
347
+ precedence, and alternative Bedrock authentication sets used by construction.
348
+ It makes no request and validates no credential value. A ready result therefore
349
+ means only “configured enough to attempt”; missing causes contain environment
350
+ names without values. Construction rejects the same missing requirements at
351
+ the provider boundary instead of deferring a known configuration failure to a
352
+ model request.
353
+
308
354
  ### §model-fact-resolution Model fact precedence
309
355
 
310
356
  Provider and model facts resolve independently:
@@ -315,7 +361,8 @@ Provider and model facts resolve independently:
315
361
  | Maximum input | Catalog `limit.input`; no generic live probe. | None. | Catalog value or `null`; never reconstructed from context and output. |
316
362
  | Maximum output | Catalog `limit.output`; no generic live probe. | None. | Minimum of catalog value and effective context, or `null`. |
317
363
  | Total output budget | None. | `PLURNK_PROVIDERS_OUTPUT_BUDGET`. | Percentage of effective context or absolute count, capped by known context/output limits; a call may only tighten it. |
318
- | Reasoning budget | None. | Optional `PLURNK_PROVIDERS_REASONING_BUDGET`. | Percentage of effective context or absolute count; valid only as a strict subset of total output and effective only while reasoning is on or adaptive. |
364
+ | Reasoning policy | Provider adapter and model capability. | `PLURNK_PROVIDERS_REASONING`, initially; durable worker selection thereafter. | One supported member of `off`, `adaptive`, `low`, `medium`, or `high`; `adaptive` is the default. |
365
+ | Reasoning budget | None. | Optional `PLURNK_PROVIDERS_REASONING_BUDGET`. | Percentage of effective context or absolute count; valid only as a strict subset of total output and effective unless reasoning is `off`. |
319
366
  | Reasoning capability | Catalog `reasoning: true`. | Runtime activation and adapter wire style. | Catalog bit remains informational; it neither activates nor blocks reasoning. |
320
367
  | Estimated USD rates | Models.dev input, output, optional reasoning, and optional cache rates. | None. | Missing differently-priced usage or rates produces unknown; exact all-zero rates produces estimated USD zero. |
321
368
 
@@ -348,12 +395,18 @@ implementation. xAI uses its documented OpenAI-compatible response directly
348
395
  because that wire includes exact cost ticks the corresponding AI SDK projection
349
396
  omits.
350
397
 
351
- Provider declarations configure facts, not credentials:
398
+ §provider-fact-authority Provider declarations configure facts, not
399
+ credentials, and Models.dev is authoritative for cataloged providers: package
400
+ defaults never redefine a cataloged provider's NPM package, endpoint, or
401
+ credential names, and one declaration's `API_KEY_ENV` holds exactly one
402
+ environment name — an ordered fallback list would paper over an
403
+ operator/catalog naming mismatch instead of reconciling it at its owning
404
+ boundary. A comma-separated value is rejected at construction.
352
405
 
353
406
  ```dotenv
354
407
  PLURNK_PROVIDERS_PROVIDER_ACME_NPM=@ai-sdk/openai-compatible
355
408
  PLURNK_PROVIDERS_PROVIDER_ACME_BASE_URL=https://api.acme.example/v1
356
- PLURNK_PROVIDERS_PROVIDER_ACME_API_KEY_ENV=ACME_API_KEY,ACME_TOKEN
409
+ PLURNK_PROVIDERS_PROVIDER_ACME_API_KEY_ENV=ACME_API_KEY
357
410
  ```
358
411
 
359
412
  The named secret remains in the operator environment. `${ENV_NAME}` inside a
@@ -375,6 +428,16 @@ A provider plugin:
375
428
  4. default-exports an AI SDK provider with `languageModel(modelId)`;
376
429
  5. peers on compatible `ai` and `@plurnk/plurnk-providers` majors.
377
430
 
431
+ §provider-grammar-transport A plugin whose backend accepts a llama.cpp-style
432
+ GBNF grammar may declare `plurnk.grammarStyle: "llamacpp"` beside its kind and
433
+ name; the discovery records it and the adapted Provider carries the capability,
434
+ so an operator-configured rail ({§grammar-rail-registration}) rides the wire
435
+ exactly as on a probed llama-server. Absence or `"none"` keeps the grammar off
436
+ the wire; any other value fails discovery loudly. The declaration is the
437
+ plugin author's fact about their backend — a wrong declaration fails at the
438
+ rail-truth boundary ({§rail-truth-engine-verdict}), never by degrading
439
+ admission.
440
+
378
441
  PLURNK adapts the returned language model. The plugin does not implement the
379
442
  PLURNK `Provider`, read PLURNK tuning knobs, or reproduce transport policy.
380
443
 
@@ -414,7 +477,9 @@ every request:
414
477
  |---|---:|---:|
415
478
  | `off` | false | `0` |
416
479
  | `adaptive` | true | configured reasoning subset, otherwise omitted |
417
- | `on` | true | configured reasoning subset, otherwise omitted |
480
+
481
+ The template control cannot express distinct fixed effort levels, so this
482
+ adapter advertises only `off` and `adaptive`.
418
483
 
419
484
  The allowance is contained by the request's total output budget. Template calls
420
485
  normally use `reasoning_format: "auto"` for a separate
@@ -451,6 +516,15 @@ First-party attribution, client, strike, workspace, loop, turn, and worker
451
516
  headers are sent only by the `plurnk` provider. They never leak to another
452
517
  backend.
453
518
 
519
+ §openrouter-app-attribution **The cataloged OpenRouter route identifies the
520
+ calling application through OpenRouter's current app-attribution headers.**
521
+ `HTTP-Referer` is the absolute HTTP(S) application URL and
522
+ `X-OpenRouter-Title` is its optional display title. The shipped floor identifies
523
+ the public Plurnk repository and may be replaced by operator configuration; an
524
+ explicitly empty `OPENROUTER_HTTP_REFERER` suppresses both headers. Attribution
525
+ applies only to the cataloged `openrouter` route and never leaks to another
526
+ provider merely because it uses the same SDK package.
527
+
454
528
  ## §9 Failures, retries, and cancellation
455
529
 
456
530
  §provider-failure-normalization Provider failures normalize to `ProviderError`.
@@ -586,7 +660,11 @@ includes reasoning receives the total directly. When a native SDK instead adds
586
660
  an explicit reasoning allowance to its generic visible-output maximum, the
587
661
  adapter sends `total - reasoning` through the generic field and the reasoning
588
662
  subset through the documented provider option. Core and other callers never
589
- reconstruct this arithmetic.
663
+ reconstruct this arithmetic. When such a backend has only a manual allowance
664
+ and no numeric subset is configured, the adapter derives that allowance from
665
+ the durable policy inside the total using the native SDK's effort proportions
666
+ and provider minimum; an envelope too small to represent the minimum fails
667
+ before provider I/O.
590
668
 
591
669
  §provider-output-budget-conformance When a completed response reports
592
670
  normalized output-token usage greater than its effective total output budget,
@@ -1,7 +1,7 @@
1
- import type { ChatMessage, PromptTokenMeasurement, Provider, ProviderCostNormalizer, ProviderGenerateArgs, ProviderRequestCapacity, ProviderResponse, ProviderUsage } from "./types.ts";
1
+ import type { ChatMessage, PromptTokenMeasurement, Provider, ProviderCostNormalizer, ProviderGenerateArgs, ProviderRequestCapacity, ProviderResponse, ProviderUsage, ReasoningPolicy } from "./types.ts";
2
2
  import type { ProviderCost } from "@plurnk/plurnk-contracts";
3
3
  import type { JSONValue } from "ai";
4
- import type { Reasoning, ReasoningResponseStyle } from "./env.ts";
4
+ import { type Reasoning, type ReasoningResponseStyle } from "./env.ts";
5
5
  import type { LanguageModel } from "ai";
6
6
  import type { PluginAttribution, PluginAttributionContext } from "@plurnk/plurnk-meta";
7
7
  export type ProviderFetch = typeof globalThis.fetch;
@@ -32,6 +32,9 @@ export type AiSdkProviderConfig = {
32
32
  maxOutputTokens?: number | null;
33
33
  outputBudget?: number | null;
34
34
  reasoningBudget?: number | null;
35
+ supportedReasoningPolicies?: readonly ReasoningPolicy[];
36
+ adaptiveReasoning?: "high" | "provider-default";
37
+ adaptiveReasoningProviderOptions?: AiSdkProviderOptions;
35
38
  additiveReasoningProvider?: "anthropic" | "bedrock";
36
39
  reasoningStyle?: ReasoningStyle;
37
40
  reasoningResponseStyle?: ReasoningResponseStyle;
@@ -69,7 +72,6 @@ export type AiSdkProviderConfig = {
69
72
  rawBody?: boolean;
70
73
  tuningFloors?: boolean;
71
74
  };
72
- export declare const effortFromBudget: (budget: number) => "low" | "medium" | "high";
73
75
  export default class AiSdkProvider implements Provider {
74
76
  #private;
75
77
  readonly attributions?: (context: PluginAttributionContext) => PluginAttribution;
@@ -80,6 +82,7 @@ export default class AiSdkProvider implements Provider {
80
82
  get maxOutputTokens(): number | null;
81
83
  get outputBudget(): number | null;
82
84
  get reasoningBudget(): number | null;
85
+ get supportedReasoningPolicies(): readonly ReasoningPolicy[];
83
86
  get inputCapacity(): number | null;
84
87
  get model(): string;
85
88
  get servedModel(): string | undefined;
@@ -1 +1 @@
1
- {"version":3,"file":"AiSdkProvider.d.ts","sourceRoot":"","sources":["../src/AiSdkProvider.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"AiSdkProvider.d.ts","sourceRoot":"","sources":["../src/AiSdkProvider.ts"],"names":[],"mappings":"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"}