@plurnk/plurnk-providers 1.3.4 → 1.3.6

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 (101) hide show
  1. package/.env.defaults +41 -52
  2. package/README.md +44 -53
  3. package/SPEC.md +215 -354
  4. package/dist/AiSdkProvider.d.ts +78 -0
  5. package/dist/AiSdkProvider.d.ts.map +1 -0
  6. package/dist/AiSdkProvider.js +591 -0
  7. package/dist/AiSdkProvider.js.map +1 -0
  8. package/dist/Mock.d.ts +1 -1
  9. package/dist/Mock.d.ts.map +1 -1
  10. package/dist/Mock.js +1 -1
  11. package/dist/Mock.js.map +1 -1
  12. package/dist/OpenAICompat.d.ts +3 -5
  13. package/dist/OpenAICompat.d.ts.map +1 -1
  14. package/dist/OpenAICompat.js +44 -133
  15. package/dist/OpenAICompat.js.map +1 -1
  16. package/dist/Pool.d.ts +1 -1
  17. package/dist/Pool.d.ts.map +1 -1
  18. package/dist/Pool.js +1 -1
  19. package/dist/Pool.js.map +1 -1
  20. package/dist/ProviderRegistry.d.ts.map +1 -1
  21. package/dist/ProviderRegistry.js +37 -24
  22. package/dist/ProviderRegistry.js.map +1 -1
  23. package/dist/aiSdkTransport.d.ts +52 -0
  24. package/dist/aiSdkTransport.d.ts.map +1 -0
  25. package/dist/aiSdkTransport.js +294 -0
  26. package/dist/aiSdkTransport.js.map +1 -0
  27. package/dist/catalogProvider.d.ts +15 -0
  28. package/dist/catalogProvider.d.ts.map +1 -0
  29. package/dist/catalogProvider.js +103 -0
  30. package/dist/catalogProvider.js.map +1 -0
  31. package/dist/compatibleProvider.d.ts +3 -0
  32. package/dist/compatibleProvider.d.ts.map +1 -0
  33. package/dist/compatibleProvider.js +146 -0
  34. package/dist/compatibleProvider.js.map +1 -0
  35. package/dist/discover.d.ts.map +1 -1
  36. package/dist/discover.js.map +1 -1
  37. package/dist/env.d.ts +1 -0
  38. package/dist/env.d.ts.map +1 -1
  39. package/dist/env.js +13 -6
  40. package/dist/env.js.map +1 -1
  41. package/dist/index.d.ts +5 -7
  42. package/dist/index.d.ts.map +1 -1
  43. package/dist/index.js +4 -8
  44. package/dist/index.js.map +1 -1
  45. package/dist/ollama.d.ts +3 -0
  46. package/dist/ollama.d.ts.map +1 -0
  47. package/dist/ollama.js +39 -0
  48. package/dist/ollama.js.map +1 -0
  49. package/dist/openai.d.ts +2 -4
  50. package/dist/openai.d.ts.map +1 -1
  51. package/dist/openai.js +1 -2
  52. package/dist/openai.js.map +1 -1
  53. package/dist/sdkModels.d.ts +13 -0
  54. package/dist/sdkModels.d.ts.map +1 -0
  55. package/dist/sdkModels.js +153 -0
  56. package/dist/sdkModels.js.map +1 -0
  57. package/dist/standardProviders.d.ts +0 -1
  58. package/dist/standardProviders.d.ts.map +1 -1
  59. package/dist/standardProviders.js +9 -11
  60. package/dist/standardProviders.js.map +1 -1
  61. package/dist/telemetry.d.ts.map +1 -1
  62. package/dist/telemetry.js +20 -9
  63. package/dist/telemetry.js.map +1 -1
  64. package/dist/types.d.ts +4 -3
  65. package/dist/types.d.ts.map +1 -1
  66. package/dist/usage.d.ts +1 -1
  67. package/dist/usage.d.ts.map +1 -1
  68. package/dist/usage.js +4 -2
  69. package/dist/usage.js.map +1 -1
  70. package/package.json +19 -8
  71. package/src/{OpenAICompat.test.ts → AiSdkProvider.test.ts} +202 -177
  72. package/src/{OpenAICompat.ts → AiSdkProvider.ts} +89 -144
  73. package/src/Mock.test.ts +3 -3
  74. package/src/Mock.ts +1 -1
  75. package/src/Pool.test.ts +3 -3
  76. package/src/Pool.ts +1 -1
  77. package/src/ProviderRegistry.test.ts +40 -27
  78. package/src/ProviderRegistry.ts +35 -24
  79. package/src/aiSdkTransport.test.ts +253 -0
  80. package/src/aiSdkTransport.ts +369 -0
  81. package/src/boundaries.test.ts +2 -2
  82. package/src/catalogProvider.test.ts +100 -0
  83. package/src/catalogProvider.ts +151 -0
  84. package/src/compatibleProvider.test.ts +44 -0
  85. package/src/compatibleProvider.ts +205 -0
  86. package/src/discover.test.ts +12 -12
  87. package/src/discover.ts +3 -6
  88. package/src/env.ts +14 -6
  89. package/src/index.ts +7 -11
  90. package/src/ollama.ts +63 -0
  91. package/src/openai.ts +2 -8
  92. package/src/sdkModels.test.ts +47 -0
  93. package/src/sdkModels.ts +194 -0
  94. package/src/telemetry.test.ts +17 -10
  95. package/src/telemetry.ts +22 -14
  96. package/src/types.ts +10 -13
  97. package/src/usage.test.ts +8 -10
  98. package/src/usage.ts +7 -3
  99. package/src/openaiStream.ts +0 -310
  100. package/src/standardProviders.test.ts +0 -949
  101. package/src/standardProviders.ts +0 -635
package/.env.defaults CHANGED
@@ -1,6 +1,6 @@
1
- # REFERENCE - @plurnk/plurnk-providers' shipped .env.defaults: the operative floor for the
2
- # PLURNK_PROVIDERS_* knobs AND the standard providers' endpoints + alias config (ecosystem
3
- # standard, providers#44: every package owns what it reads; the file IS the documentation).
1
+ # REFERENCE - @plurnk/plurnk-providers' shipped .env.defaults: the operative floor for
2
+ # PLURNK_PROVIDERS_* knobs and provider declarations (providers#44: every package owns
3
+ # what it reads; the file IS the configuration reference).
4
4
  # The daemon assembles every installed member's file into one floor (set-if-unset under the
5
5
  # operator's env) - do NOT edit this file; put YOUR config in ~/.plurnk/.env or ./.env. A key
6
6
  # claimed by two packages crashes boot naming both.
@@ -9,10 +9,9 @@
9
9
  # the bare name (suffix case-folds; SPEC §4). Set lines are the floor; commented lines are values
10
10
  # whose UNSET state is meaningful (derive/auto/off, or a required secret) - uncomment to pin.
11
11
  #
12
- # Base URLs are SHIPPED DEFAULTS - the canonical vendor endpoint lives HERE (overridable in your
13
- # .env, or per-alias via PLURNK_BASEURL_<alias>), so the happy path needs ZERO endpoint config.
14
- # The ONLY required per-provider input is the API KEY: a secret with no default, set in your own
15
- # .env; an unset key for a provider you actually use fails hard at construction naming the var.
12
+ # Models.dev supplies cataloged providers' SDK package, endpoint, credential names,
13
+ # model metadata, and prices. Operator declarations below cover only facts absent
14
+ # from or deliberately overridden over that catalog. Secret VALUES never belong here.
16
15
 
17
16
  # --- Side-channel reasoning (SPEC §4, #32/#33/#399) ---
18
17
  # ACTIVATION and BUDGET are separate so a numeric can never silently flip wire flags.
@@ -32,16 +31,19 @@ PLURNK_PROVIDERS_REASONING=adaptive
32
31
  # the floor the provider manages wherever a grammar rides (greedy-under-mask loops without it).
33
32
  PLURNK_PROVIDERS_TEMPERATURE=0.2
34
33
  PLURNK_PROVIDERS_REPEAT_PENALTY=1.15
35
- # FREQUENCY_PENALTY (#426): the anti-degeneration guard on the CLOUD path. repeat_penalty is a
36
- # llama.cpp/vLLM MULTIPLIER the plain cloud path (grammarStyle "none") can't use; frequency_penalty
37
- # is OpenAI-standard, so every OpenAI-compat backend accepts it (verified live: together, deepinfra,
38
- # fireworks). Without it a cloud alias ran the sampler bare and looped to the token cap. 0 = off.
39
- # NOTE: 0.4 is a STARTING value (acceptance-verified, not yet effectiveness-benched) - raise it if a
40
- # firefast/deepseek re-bench still degenerates.
41
- PLURNK_PROVIDERS_FREQUENCY_PENALTY=0.4
34
+ # FREQUENCY_PENALTY (#426): optional cloud anti-degeneration tuning. API acceptance
35
+ # permits the field to ride but does not establish its semantic effect, and provider
36
+ # implementations differ. The portable floor is off; enable per alias only from
37
+ # provider documentation or a controlled behavioral experiment.
38
+ PLURNK_PROVIDERS_FREQUENCY_PENALTY=0
39
+ # PLURNK_PROVIDERS_FREQUENCY_PENALTY_myendpoint=0.4
42
40
  # Fixed provider service tier. Fireworks accepts auto|default|flex|priority;
43
41
  # normally set per alias so a paid routing choice is explicit.
44
42
  # PLURNK_PROVIDERS_SERVICE_TIER_myfireworks=priority
43
+ # Compatible endpoints verified to accept the OpenAI prompt_cache_key use the
44
+ # stable worker id for replica-local prefix affinity. Official native SDKs own
45
+ # their cache mechanisms and do not receive this compatible extension.
46
+ PLURNK_PROVIDERS_PROMPT_CACHE_KEY=1
45
47
  # #567: DRY loop-breaker - llama.cpp-only (grammarStyle "none" paths skip it). MULTIPLIER=0
46
48
  # disables DRY at the general floor: the #567 sweep showed L=2 is WORSE than DRY-off on both
47
49
  # runaways AND corruption; L=32 is the measured plurnk-safe threshold (0 corruption fails,
@@ -64,7 +66,6 @@ PLURNK_PROVIDERS_STREAM_IDLE_TIMEOUT=0
64
66
  # Transient-failure retries: 0 = surface the first failure; N = retries on 429/5xx/timeout
65
67
  # with exponential backoff (Retry-After wins). RETRY_DELAY is the backoff base (ms).
66
68
  PLURNK_PROVIDERS_RETRY_ATTEMPTS=3
67
- PLURNK_PROVIDERS_RETRY_DELAY=2000
68
69
 
69
70
  # --- Endpoint probe (#34) ---
70
71
  # GET /v1/models at construction (context window + llama-server fingerprint). One failure
@@ -101,6 +102,27 @@ PLURNK_PROVIDERS_PROBE_DELAY=250
101
102
  # PLURNK_PROVIDERS_TOP_LOGPROBS_myscraper=3
102
103
  # PLURNK_PROVIDERS_RAWBODY_myscraper=1
103
104
 
105
+ # --- Provider declarations (SPEC §5) ---
106
+ # Models.dev supplies the AI SDK package, credential names, endpoint, and model
107
+ # metadata for cataloged providers. These knobs override those facts or declare
108
+ # an endpoint Models.dev does not list. NAME is the alias provider segment.
109
+ # PLURNK_PROVIDERS_PROVIDER_<NAME>_NPM=<supported AI SDK package>
110
+ # PLURNK_PROVIDERS_PROVIDER_<NAME>_BASE_URL=<endpoint>
111
+ # PLURNK_PROVIDERS_PROVIDER_<NAME>_API_KEY_ENV=<comma-separated env names>
112
+ PLURNK_PROVIDERS_PROVIDER_CLOUDFLARE_API_KEY_ENV=CLOUDFLARE_API_TOKEN,CLOUDFLARE_API_KEY
113
+ # Fireworks reasoners default on when reasoning_effort is omitted; explicit
114
+ # "none" is its off switch. This is a declared wire exception, not a registry.
115
+ PLURNK_PROVIDERS_PROVIDER_FIREWORKS_REASONING_STYLE=effort_explicit
116
+ PLURNK_PROVIDERS_PROVIDER_VOLCENGINE_NPM=@ai-sdk/openai-compatible
117
+ PLURNK_PROVIDERS_PROVIDER_VOLCENGINE_BASE_URL=https://ark.ap-southeast.bytepluses.com/api/v3
118
+ PLURNK_PROVIDERS_PROVIDER_VOLCENGINE_API_KEY_ENV=ARK_API_KEY
119
+ PLURNK_PROVIDERS_PROVIDER_BAICHUAN_NPM=@ai-sdk/openai-compatible
120
+ PLURNK_PROVIDERS_PROVIDER_BAICHUAN_BASE_URL=https://api.baichuan-ai.com/v1
121
+ PLURNK_PROVIDERS_PROVIDER_BAICHUAN_API_KEY_ENV=BAICHUAN_API_KEY
122
+ PLURNK_PROVIDERS_PROVIDER_QIANFAN_NPM=@ai-sdk/openai-compatible
123
+ PLURNK_PROVIDERS_PROVIDER_QIANFAN_BASE_URL=https://qianfan.baidubce.com/v2
124
+ PLURNK_PROVIDERS_PROVIDER_QIANFAN_API_KEY_ENV=QIANFAN_API_KEY
125
+
104
126
  # --- Alias cascade (SPEC §5) - declare aliases, then pick the active one ---
105
127
  # First path segment is the provider name; the rest is the provider-native model id (may
106
128
  # contain "/"). Operator-specific, no default - the examples are commented.
@@ -117,44 +139,11 @@ PLURNK_PROVIDERS_PROBE_DELAY=250
117
139
  # PLURNK_MODEL_NOOK=ollama/qwen2.5-coder
118
140
  # PLURNK_BASEURL_NOOK=http://nook:11434
119
141
 
120
- # --- Standard provider endpoints (frozen table) ---
121
- # Base URLs ship at their canonical vendor default - zero endpoint config for the happy path.
122
- # Override in your .env (proxy/self-host/regional twin), or per-alias with PLURNK_BASEURL_<alias>
123
- # (which wins over these). Each provider ALSO needs its API KEY - a required secret with no
124
- # default, set in ~/.plurnk/.env; the key var mirrors the *_BASE_URL prefix (FIREWORKS_API_KEY,
125
- # ...) except where noted. An unset key fails hard at construction naming the var.
126
-
127
- # Generic OpenAI-compat - OpenAI proper by default; for a local llama-server/vLLM, override the
128
- # endpoint per-alias (PLURNK_BASEURL_<alias>). OPENAI_API_BASE is a legacy URL alias.
142
+ # The compatible `openai` and first-party `plurnk` adapters are intentionally
143
+ # local contracts rather than catalog declarations. OpenAI defaults to its
144
+ # canonical endpoint; override it per alias for llama-server or vLLM.
129
145
  OPENAI_BASE_URL=https://api.openai.com/v1
130
- GROQ_BASE_URL=https://api.groq.com/openai/v1
131
- DEEPSEEK_BASE_URL=https://api.deepseek.com/v1
132
- MISTRAL_BASE_URL=https://api.mistral.ai/v1
133
- TOGETHER_BASE_URL=https://api.together.xyz/v1
134
- FIREWORKS_BASE_URL=https://api.fireworks.ai/inference/v1
135
- DEEPINFRA_BASE_URL=https://api.deepinfra.com/v1/openai # key aliases: DEEPINFRA_API_TOKEN, DEEPINFRA_TOKEN
136
-
137
- # Chinese cloud hosts - base ships INTERNATIONAL; mainland operators repoint *_BASE_URL at the `.cn` twin.
138
- MOONSHOT_BASE_URL=https://api.moonshot.ai/v1
139
- DASHSCOPE_BASE_URL=https://dashscope-intl.aliyuncs.com/compatible-mode/v1 # Alibaba Qwen
140
- ZHIPU_BASE_URL=https://api.z.ai/api/paas/v4 # Zhipu GLM; key ZHIPUAI_API_KEY (alias ZAI_API_KEY)
141
- ARK_BASE_URL=https://ark.ap-southeast.bytepluses.com/api/v3 # ByteDance Doubao (BytePlus ModelArk)
142
- HUNYUAN_BASE_URL=https://api.hunyuan.cloud.tencent.com/v1 # Tencent Hunyuan
143
- MINIMAX_BASE_URL=https://api.minimax.io/v1
144
- STEPFUN_BASE_URL=https://api.stepfun.com/v1 # StepFun; key STEP_API_KEY
145
- BAICHUAN_BASE_URL=https://api.baichuan-ai.com/v1
146
- QIANFAN_BASE_URL=https://qianfan.baidubce.com/v2 # Baidu ERNIE (Qianfan v2)
147
- SILICONFLOW_BASE_URL=https://api.siliconflow.com/v1
148
- MODELSCOPE_BASE_URL=https://api-inference.modelscope.cn/v1 # key alias: MODELSCOPE_TOKEN
149
-
150
- # First-party Claude (Anthropic's OpenAI-compat endpoint).
151
- ANTHROPIC_BASE_URL=https://api.anthropic.com/v1
152
-
153
- # AWS Bedrock (OpenAI-compat path /openai/v1) - base is REGION-templated: leave unset to derive
154
- # from AWS_REGION / AWS_DEFAULT_REGION, or pin explicitly. No static default. Key AWS_BEARER_TOKEN_BEDROCK.
155
- # BEDROCK_BASE_URL=https://bedrock-runtime.us-east-1.amazonaws.com/openai/v1
156
-
157
- # plurnk hosted model - PLURNK_API_KEY is an OPTIONAL bearer (sent only when set).
146
+ # PLURNK_API_KEY is an optional bearer; the endpoint is eventually keyless.
158
147
  PLURNK_BASE_URL=https://plurnk.ai/v1
159
148
  # PLURNK_BASE_URL=http://plurnksnr2kihuukt6v22ko72r34dxeatbsfhgow3hvnlw6btanxphad.onion/v1 # Tor
160
149
 
package/README.md CHANGED
@@ -1,35 +1,48 @@
1
1
  # @plurnk/plurnk-providers
2
2
 
3
- Provider contract and shared transports for PLURNK model backends.
3
+ PLURNK's stable model-provider contract and its adapter to the
4
+ [AI SDK](https://ai-sdk.dev/).
4
5
 
5
- The package includes:
6
+ Ordinary provider behavior is intentionally not reimplemented here:
6
7
 
7
- - provider interfaces and normalized responses;
8
- - OpenAI-compatible streaming transport;
9
- - standard provider configuration;
10
- - alias resolution and provider discovery;
11
- - usage, cost, reasoning, grammar, and telemetry normalization.
8
+ - Models.dev supplies provider package, endpoint, credential, context-window,
9
+ output-limit, and pricing metadata at build time.
10
+ - Official AI SDK providers own vendor request and response protocols.
11
+ - PLURNK owns aliases, generation envelopes, normalized usage and errors,
12
+ evidence capture, first-party metadata, and local endpoint capabilities.
12
13
 
13
- See `SPEC.md` for the complete API and `.env.defaults` for configuration.
14
+ See `SPEC.md` for the contract and `.env.defaults` for every operational knob.
14
15
 
15
- ## Standard providers
16
+ ## Configure a model
16
17
 
17
- Backends compatible with the shared transport are configured by the standard
18
- provider table and do not require a separate package. An alias selects a
19
- provider and model:
18
+ Declare an alias, then select it:
20
19
 
21
20
  ```dotenv
22
- PLURNK_MODEL_fast=openai/gpt-4.1-mini
21
+ PLURNK_MODEL_fast=openai/gpt-5-mini
23
22
  PLURNK_MODEL=fast
24
23
  OPENAI_API_KEY=...
25
24
  ```
26
25
 
27
- Provider-specific packages are appropriate when a backend requires a distinct
28
- protocol, discovery step, authentication flow, or response normalization.
26
+ Cataloged providers need no endpoint declaration. To add an
27
+ OpenAI-compatible provider that Models.dev does not describe:
28
+
29
+ ```dotenv
30
+ PLURNK_PROVIDERS_PROVIDER_ACME_NPM=@ai-sdk/openai-compatible
31
+ PLURNK_PROVIDERS_PROVIDER_ACME_BASE_URL=https://api.acme.example/v1
32
+ PLURNK_PROVIDERS_PROVIDER_ACME_API_KEY_ENV=ACME_API_KEY
33
+ PLURNK_MODEL_acme=acme/model-id
34
+ ```
35
+
36
+ Provider declarations are configuration, not secrets. Secret values remain in
37
+ the operator environment.
29
38
 
30
39
  ## Provider plugins
31
40
 
32
- A provider plugin may use any npm scope. Declare its identity:
41
+ Most integrations should use an MCP server, executor, scheme, or a provider
42
+ declaration. A provider plugin is only needed for a protocol binding unavailable
43
+ through the catalog and installed SDK packages.
44
+
45
+ It may use any npm scope. Its package manifest declares the PLURNK name:
33
46
 
34
47
  ```json
35
48
  {
@@ -38,51 +51,29 @@ A provider plugin may use any npm scope. Declare its identity:
38
51
  "name": "acme"
39
52
  },
40
53
  "peerDependencies": {
41
- "@plurnk/plurnk-providers": "^1.2.0"
54
+ "@plurnk/plurnk-providers": "^1.2.0",
55
+ "ai": "^6.0.0"
42
56
  }
43
57
  }
44
58
  ```
45
59
 
46
- Default-export a factory compatible with `ProviderFactory`. The factory receives
47
- the environment, model name, and optional per-alias base URL. It returns a
48
- `Provider` synchronously or asynchronously.
49
-
50
- Packages using an OpenAI-compatible API should construct
51
- `OpenAICompatProvider`; other protocols implement `Provider` directly.
52
-
53
- The runtime-neutral `@plurnk/plurnk-providers/openai` entrypoint exports the
54
- OpenAI-compatible provider and its Web API transport types without importing
55
- package discovery, environment loading, or the provider registry. A consumer
56
- with its own request facility can inject a fetch-compatible implementation per
57
- instance:
58
-
59
- ```ts
60
- import { OpenAICompatProvider } from "@plurnk/plurnk-providers/openai";
61
-
62
- const provider = new OpenAICompatProvider({
63
- ...config,
64
- fetch: providerFetch,
65
- });
66
- ```
67
-
68
- The injected function receives the same URL, headers, body, and `AbortSignal`
69
- as the default `globalThis.fetch`. It owns only execution of that request;
70
- request shaping, response parsing, retries, usage, reasoning, raw capture, and
71
- telemetry remain provider behavior. Vendor binding adapters and their
72
- configuration belong to the consuming integration.
60
+ The default export is an AI SDK provider with
61
+ `languageModel(modelId)`. PLURNK adapts that language model into its own
62
+ contract, so plugins do not reproduce retries, usage normalization, envelopes,
63
+ or telemetry.
73
64
 
74
- Discovery scans installed npm packages for `plurnk.kind === "provider"`.
75
- Duplicate provider names are errors. `PLURNK_PLUGINS_TRUSTED_ONLY` can restrict
76
- third-party discovery.
65
+ Discovery is scope-agnostic and rejects duplicate names.
66
+ `PLURNK_PLUGINS_TRUSTED_ONLY` restricts third-party discovery.
77
67
 
78
- ## Version compatibility
68
+ ## Local endpoints
79
69
 
80
- Provider plugins declare the compatible provider-framework range with normal
81
- peer dependency semantics. `plurnk.builtAgainst` records the exact framework
82
- version used to test the published artifact. Compatible framework patches do
83
- not require republishing an unchanged plugin.
70
+ `openai` and `ollama` retain small in-package adapters because local operation
71
+ requires runtime facts no static catalog owns: served model, context window,
72
+ llama-server capabilities, slots, EOS token, and exact tokenization.
84
73
 
85
- Do not use npm force flags to install an incompatible peer graph.
74
+ The `plurnk` provider retains the compatible transport because it carries
75
+ first-party attribution and loop metadata and leaves model tuning to the
76
+ endpoint.
86
77
 
87
78
  ## Development
88
79