@oh-my-pi/pi-catalog 18.2.7 → 18.2.9

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 (57) hide show
  1. package/CHANGELOG.md +26 -3
  2. package/README.md +18 -18
  3. package/dist/types/compat/auth-ids.d.ts +2 -2
  4. package/dist/types/compat/axes.d.ts +2 -2
  5. package/dist/types/compat/catalog-policy.d.ts +7 -0
  6. package/dist/types/compat/output-limits.d.ts +3 -0
  7. package/dist/types/compat/provider-ids.d.ts +1 -1
  8. package/dist/types/compat/tools.d.ts +5 -0
  9. package/dist/types/compat/types.d.ts +2 -2
  10. package/dist/types/provider-models/openai-compat.d.ts +26 -0
  11. package/dist/types/types.d.ts +5 -2
  12. package/dist/types/wire/singularityapi.d.ts +29 -0
  13. package/package.json +38 -38
  14. package/src/compat/auth-ids.ts +4 -0
  15. package/src/compat/axes.ts +21 -2
  16. package/src/compat/catalog-policy.ts +28 -0
  17. package/src/compat/output-limits.ts +12 -0
  18. package/src/compat/provider-ids.ts +2 -0
  19. package/src/compat/resolve.ts +4 -2
  20. package/src/compat/rules/README.md +34 -33
  21. package/src/compat/rules/auth/_order.kdl +1 -1
  22. package/src/compat/rules/auth/singularityapi-dev.kdl +22 -0
  23. package/src/compat/rules/auth/singularityapi-tech.kdl +23 -0
  24. package/src/compat/rules/classes/gpt-oss.kdl +3 -0
  25. package/src/compat/rules/classes/xai.kdl +3 -3
  26. package/src/compat/rules/providers/amazon-bedrock.kdl +1 -1
  27. package/src/compat/rules/providers/anthropic.kdl +1 -1
  28. package/src/compat/rules/providers/cloudflare-ai-gateway.kdl +1 -1
  29. package/src/compat/rules/providers/commandcode.kdl +1 -1
  30. package/src/compat/rules/providers/cursor.kdl +1 -1
  31. package/src/compat/rules/providers/google-antigravity.kdl +5 -0
  32. package/src/compat/rules/providers/kilo.kdl +1 -1
  33. package/src/compat/rules/providers/litellm.kdl +1 -1
  34. package/src/compat/rules/providers/native-tools.kdl +4 -0
  35. package/src/compat/rules/providers/openai.kdl +58 -0
  36. package/src/compat/rules/providers/opencode-zen.kdl +1 -1
  37. package/src/compat/rules/providers/openrouter.kdl +108 -0
  38. package/src/compat/rules/providers/output-limits.kdl +4 -0
  39. package/src/compat/rules/providers/singularityapi-dev.kdl +92 -0
  40. package/src/compat/rules/providers/singularityapi-tech.kdl +72 -0
  41. package/src/compat/rules/providers/tool-free-history.kdl +6 -0
  42. package/src/compat/rules/providers/vercel-ai-gateway.kdl +1 -1
  43. package/src/compat/rules/providers/xai-oauth.kdl +8 -1
  44. package/src/compat/rules/providers/xai.kdl +4 -4
  45. package/src/compat/rules/providers/xiaomi-token-plan-cn.kdl +23 -0
  46. package/src/compat/rules/providers/zenmux.kdl +1 -1
  47. package/src/compat/rules/runtime/behavior.kdl +2 -0
  48. package/src/compat/rules.json +1 -1
  49. package/src/compat/tools.ts +12 -0
  50. package/src/compat/types.ts +2 -2
  51. package/src/discovery/devin.ts +59 -34
  52. package/src/models.json +1 -1
  53. package/src/provider-models/cache-provider-id.ts +31 -0
  54. package/src/provider-models/descriptors.ts +4 -0
  55. package/src/provider-models/openai-compat.ts +390 -119
  56. package/src/types.ts +19 -1
  57. package/src/wire/singularityapi.ts +34 -0
@@ -50,14 +50,14 @@ class "anthropic" {
50
50
 
51
51
  Classification trims and lowercases the full model identifier. The **bare name** is the segment after its final `/`. Matcher tokens are also lowercased while parsing.
52
52
 
53
- | Node | Rank | Match |
54
- | --- | ---: | --- |
55
- | `exact "token"` | 4 | The whole bare name equals `token`. |
56
- | `bounded "token"` | 3 | The bare name equals `token`, or starts with it followed by `-`, `_`, `.`, `:`, or an ASCII digit. |
57
- | `namespace "token"` | 2 | A non-empty `/`-separated segment of the full identifier equals `token`. |
58
- | `namespace "token" bounded=#true` | 2 | Split the full identifier on `/`, `.`, and `:`; a segment must satisfy the bounded rule above. This is the only matcher property. |
59
- | `prefix "token"` | 1 | The bare name starts with `token`. |
60
- | `glob "pattern"` | 0 | An anchored `*` wildcard match over the bare name. `*` spans any substring; all non-wildcard text remains anchored in order. |
53
+ | Node | Rank | Match |
54
+ | --------------------------------- | ---: | --------------------------------------------------------------------------------------------------------------------------------- |
55
+ | `exact "token"` | 4 | The whole bare name equals `token`. |
56
+ | `bounded "token"` | 3 | The bare name equals `token`, or starts with it followed by `-`, `_`, `.`, `:`, or an ASCII digit. |
57
+ | `namespace "token"` | 2 | A non-empty `/`-separated segment of the full identifier equals `token`. |
58
+ | `namespace "token" bounded=#true` | 2 | Split the full identifier on `/`, `.`, and `:`; a segment must satisfy the bounded rule above. This is the only matcher property. |
59
+ | `prefix "token"` | 1 | The bare name starts with `token`. |
60
+ | `glob "pattern"` | 0 | An anchored `*` wildcard match over the bare name. `*` spans any substring; all non-wildcard text remains anchored in order. |
61
61
 
62
62
  A class match is ranked by `(matcher-kind rank, token byte length)`. The greatest tuple wins. Equal tuples from different classes are an ambiguity error; source order is not a tiebreak. If nothing matches, classification returns class `unknown` with no family or revision.
63
63
 
@@ -93,16 +93,16 @@ revision skip-bare "o1" "o3" "o4"
93
93
 
94
94
  Optional properties are:
95
95
 
96
- | Property | Shape and meaning |
97
- | --- | --- |
98
- | `provider` | Exact provider key, compared case-insensitively. A matching provider-specific override wins over a provider-agnostic one. |
99
- | `logical` | Corrected logical model identifier. |
100
- | `class` | Corrected class ID; a non-empty string. |
101
- | `family` | Corrected product-family ID; a non-empty string. |
102
- | `revision` | One to three unsigned 8-bit components separated by `.` or `-`. |
103
- | `effort` | `off`, `minimal`, `low`, `medium`, `high`, `xhigh`, or `max`. |
104
- | `thinking-variant` | Boolean marker for a separately exposed thinking sibling. |
105
- | `expires-at-ms` | Non-negative Unix time in milliseconds. The override is inactive when the observation time is at or after this value. |
96
+ | Property | Shape and meaning |
97
+ | ------------------ | ------------------------------------------------------------------------------------------------------------------------- |
98
+ | `provider` | Exact provider key, compared case-insensitively. A matching provider-specific override wins over a provider-agnostic one. |
99
+ | `logical` | Corrected logical model identifier. |
100
+ | `class` | Corrected class ID; a non-empty string. |
101
+ | `family` | Corrected product-family ID; a non-empty string. |
102
+ | `revision` | One to three unsigned 8-bit components separated by `.` or `-`. |
103
+ | `effort` | `off`, `minimal`, `low`, `medium`, `high`, `xhigh`, or `max`. |
104
+ | `thinking-variant` | Boolean marker for a separately exposed thinking sibling. |
105
+ | `expires-at-ms` | Non-negative Unix time in milliseconds. The override is inactive when the observation time is at or after this value. |
106
106
 
107
107
  The tuple `(provider, selector-kind, selector)` must also be unique, including provider-agnostic selectors. Active exact overrides take precedence over every glob. Within each selector kind, provider-scoped overrides precede provider-agnostic ones; matching globs rank by non-wildcard byte count. Equal-ranked globs are an ambiguity error, never resolved by declaration order. When no observation time is supplied, an expiring override remains active.
108
108
 
@@ -124,6 +124,7 @@ collapse {
124
124
  provider-alias "devin" "opus" "claude-opus-5"
125
125
  }
126
126
  ```
127
+
127
128
  `variant-family` declares one reviewed provider-scoped collapsed family: positional provider and logical id, `name=` display name, and a body of `members "a" "b" …` (wire ids in priority order), `route "<tier>" "<wire-id>"` per effort tier (`off` included), and optional `mode`, `efforts`, `default-level`, `default-member`, `retired-members`, `effort-budget "<tier>" <n>`, `requires-effort`, `suppress-when-off`, `no-thinking`, `preserve-absent-effort-routes`, and `extra-aliases`. A `{rev}` placeholder in the logical id makes the node a **template**: it is instantiated once per revision found in live ids (`gemini-{rev}-flash` matches `gemini-3.8-flash-low` → family `gemini-3.8-flash`), every wire id in the body and the `name=` carry the same placeholder, and an optional `revision=` constraint (`">=3.6"`) bounds the generations it applies to. A concrete family with the same instantiated id wins over the template. `provider-alias` maps one provider-scoped selector spelling onto a logical id without making it a family member.
128
129
 
129
130
  `thinking-suffix` accepts one non-empty suffix and no properties. `pair-token` declares bounded (possibly infix) tokens naming the thinking sibling of a live bare twin (`sonar-reasoning-pro` beside `sonar-pro`); it drives thinking-pair derivation only — never identity suffix collapse — and negated `no-`/`non-` forms never match. `effort-suffix` additionally requires `tier` with one of the effort values above, and may have `except-bare-prefix`. `routing-variant-suffix` takes one non-empty suffix followed by one or more provider IDs: a wire identifier carrying the suffix on one of those providers is a **routing variant** of its plain identifier — discovery derives base-model metadata from the plain bundled SKU while keeping the suffixed wire identifier for requests; routing variants never participate in effort collapse. `effort-lane-suffix` takes one non-empty lane suffix followed by one or more provider IDs, plus an optional `bare-prefix` gate: on a declared provider, an identifier ending in the lane suffix collapses the effort suffix wedged before the lane token while keeping the lane on the logical id. `effort-family` takes a provider, the canonical logical id, and zero or more exact aliases that fold onto it.
@@ -151,7 +152,7 @@ discovery {
151
152
 
152
153
  ## Cascade grammar
153
154
 
154
- A cascade document starts with `class` or `provider`. Every selector adds a conjunct to the current rule. `on` scopes by deployment provider; `on-api` scopes by request adapter, including custom provider names. Axis directives may appear directly in any permitted scope, and nested selector blocks may appear alongside them.
155
+ A cascade document starts with `class`, `provider`, or `on-api`. Root `on-api` declares a transport contract independent of model identity and provider name. Every selector adds a conjunct to the current rule. `on` scopes by deployment provider; `on-api` scopes by request adapter, including custom provider names. Axis directives may appear directly in any permitted scope, and nested selector blocks may appear alongside them.
155
156
 
156
157
  ```kdl
157
158
  class "gemini" {
@@ -178,15 +179,15 @@ provider "openrouter" {
178
179
 
179
180
  ### Selectors and nesting
180
181
 
181
- | Selector | Form | Matching semantics |
182
- | --- | --- | --- |
183
- | `class` | `class "id" { ... }` | Exact class ID. At document root it may contain `on`, `on-api`, `family`, `revision`, and `models`. Under `provider` it may contain `family`, `revision`, and `models`. |
184
- | `provider` | `provider "id" { ... }` | Exact provider ID. It is root-only and may contain `class` and `models`. |
185
- | `on` | `on "provider-a" "provider-b" { ... }` | One or more provider IDs, combined as OR. It is allowed only under a root `class`, and may contain `family`, `revision`, and `models`. |
186
- | `on-api` | `on-api "adapter-a" "adapter-b" { ... }` | One or more request adapter IDs, combined as OR. It is allowed only under a root `class`, and may contain `family`, `revision`, and `models`. |
187
- | `family` | `family "id" { ... }` | Exact classified family ID. It may contain `revision` and `models`. A target with no family does not match. |
188
- | `revision` | `revision ">=2.5 <4" { ... }` | A non-empty, whitespace-separated conjunction of comparisons. It may contain `models`. A target with no revision does not match. |
189
- | `models` | `models "id" "vendor/*" { ... }` | One or more alternatives, combined as OR. It cannot contain another selector. `token="name"` matches an ASCII-case-insensitive token bounded by non-alphanumerics. |
182
+ | Selector | Form | Matching semantics |
183
+ | ---------- | ---------------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
184
+ | `class` | `class "id" { ... }` | Exact class ID. At document root it may contain `on`, `on-api`, `family`, `revision`, and `models`. Under `provider` it may contain `family`, `revision`, and `models`. |
185
+ | `provider` | `provider "id" { ... }` | Exact provider ID. It is root-only and may contain `class` and `models`. |
186
+ | `on` | `on "provider-a" "provider-b" { ... }` | One or more provider IDs, combined as OR. It is allowed only under a root `class`, and may contain `family`, `revision`, and `models`. |
187
+ | `on-api` | `on-api "adapter-a" "adapter-b" { ... }` | One or more request adapter IDs, combined as OR. At document root it may contain `class` and `models`; under a root `class` it may contain `family`, `revision`, and `models`. |
188
+ | `family` | `family "id" { ... }` | Exact classified family ID. It may contain `revision` and `models`. A target with no family does not match. |
189
+ | `revision` | `revision ">=2.5 <4" { ... }` | A non-empty, whitespace-separated conjunction of comparisons. It may contain `models`. A target with no revision does not match. |
190
+ | `models` | `models "id" "vendor/*" { ... }` | One or more alternatives, combined as OR. It cannot contain another selector. `token="name"` matches an ASCII-case-insensitive token bounded by non-alphanumerics. |
190
191
 
191
192
  Class, provider/`on`, `on-api`, and family selector values are compared exactly and case-sensitively to the structured resolve target. Revision operators are `>=`, `>`, `<=`, `<`, and `=`; operands have one to three dot-separated unsigned 8-bit components, omitted components zero.
192
193
 
@@ -401,17 +402,17 @@ Only `discovery` enrolls a provider in `generate-models.ts`; providers without i
401
402
 
402
403
  ### Seed rows
403
404
 
404
- A `seed` *defines* bundled rows for providers whose catalog cannot be discovered at generation time — credential-scoped rosters, unauthenticated regens, or models ahead of upstream catalogs. Every other stratum patches rows; this one authors them. Runtime model managers hand the rows to `staticModels` through `seedModels(provider)`; the generator bundles them per the seed's `bundle` policy. Values are literal — a seed never derives from another provider's row, and pricing is never borrowed.
405
+ A `seed` _defines_ bundled rows for providers whose catalog cannot be discovered at generation time — credential-scoped rosters, unauthenticated regens, or models ahead of upstream catalogs. Every other stratum patches rows; this one authors them. Runtime model managers hand the rows to `staticModels` through `seedModels(provider)`; the generator bundles them per the seed's `bundle` policy. Values are literal — a seed never derives from another provider's row, and pricing is never borrowed.
405
406
 
406
407
  `seed` properties: `api` and `base-url` are per-row defaults (a `model` may override either with the same property names); `bundle` defaults to `always`; `precedence="seed"` is optional. `model` takes the wire id positionally, requires `name=`, and its body MUST declare `reasoning`, `input` (`"text"` and/or `"image"`), `cost` (all four per-million rates), and `limits` (`context=` / `max-tokens=`, an omitted limit is `null`); `supports-tools #true` is optional. Any other directive is an axis from the cascade vocabulary: thinking axes become the row's explicit `thinking` (then `thinking-mode` and `thinking-efforts` are both required), wire axes become its explicit `compat` and must apply to the row's API, and catalog axes are rejected because they stay rule-owned in the cascade block. Explicit `thinking`/`compat` on a seed row win over the cascade exactly as they do for any authored spec.
407
408
 
408
409
  `bundle` decides when the generator includes the rows:
409
410
 
410
- | Policy | Rows enter the bundle |
411
- | --- | --- |
412
- | `always` | Every regeneration. Same-id upstream/discovery rows win dedup. |
411
+ | Policy | Rows enter the bundle |
412
+ | ---------- | ------------------------------------------------------------------------- |
413
+ | `always` | Every regeneration. Same-id upstream/discovery rows win dedup. |
413
414
  | `fallback` | Only when the provider's authoritative catalog discovery did not succeed. |
414
- | `empty` | Only when no other source produced a row for the provider. |
415
+ | `empty` | Only when no other source produced a row for the provider. |
415
416
 
416
417
  `precedence="seed"` prepends the rows after the previous-snapshot merge and cross-provider reference fills, so the authored row wins dedup and same-id rows on other hosts never overwrite its name or capabilities (QwenCloud Token Plan, Meta). The default `upstream` precedence appends before the snapshot merge, so the current seed — not a stale snapshot copy — is the fallback row.
417
418
 
@@ -10,4 +10,4 @@ login-order "openai-codex" "anthropic" "zai" "zai-coding-plan" "kimi-code" "open
10
10
  "qianfan" "venice" "siliconflow" "siliconflow-cn" "synthetic" "nanogpt" "wafer-serverless" "coreweave" \
11
11
  "vercel-ai-gateway" "cloudflare-ai-gateway" "litellm" "kilo" "zenmux" "opencode-zen" "opencode-go" \
12
12
  "yolo-auto" "tavily" "kagi" "exa" "parallel" "typesafe" "ollama" "ollama-cloud" "lm-studio" "llama.cpp" "vllm" \
13
- "gmi-cloud" "stencil"
13
+ "gmi-cloud" "stencil" "singularityapi-dev" "singularityapi-tech"
@@ -0,0 +1,22 @@
1
+ // SingularityAPI universal inference gateway (api.singularityapi.dev): 300+
2
+ // models behind one OpenAI-compatible endpoint, pay-as-you-go `sk-sapi-...`
3
+ // bearer keys, per-million-token tariffs published per model. SingularityAPI
4
+ // ships two unrelated products behind one brand — this gateway and the
5
+ // slot-reserved DeepSeek lanes on api.singularityapi.tech — with disjoint
6
+ // keys, dashboards, effort ladders, and billing, so each owns its own
7
+ // provider id, env var, and login flow (neither key works on the other host,
8
+ // verified 2026-09-22).
9
+ // Key validation probes the non-billable `GET /v1/models`: it answers 401
10
+ // `invalid_api_key` for a missing, malformed, or unknown key (verified
11
+ // 2026-09-22), so a bad key is rejected without spending.
12
+ auth "singularityapi-dev" {
13
+ name "SingularityAPI"
14
+ env "SINGULARITYAPI_DEV_API_KEY"
15
+ login "api-key" {
16
+ auth-url "https://app.singularityapi.dev"
17
+ instructions "Create an API key from the SingularityAPI dashboard, then paste it here"
18
+ prompt "Paste your SingularityAPI API key" placeholder="sk-sapi-..."
19
+ normalize "strip-bearer"
20
+ validate "models-endpoint" label="SingularityAPI" url="https://api.singularityapi.dev/v1/models"
21
+ }
22
+ }
@@ -0,0 +1,23 @@
1
+ // SingularityAPI reserved DeepSeek lanes (api.singularityapi.tech, a LiteLLM
2
+ // front end in front of slot-reserved lanes) — the vendor's other product,
3
+ // separated from api.singularityapi.dev because the two share no key, no
4
+ // billing model, and no effort ladder. Usage here is charged against a booked
5
+ // reservation slot rather than prepaid credit: a valid key with no active
6
+ // slot answers 403 `permission_error` ("No active lane reservation for this
7
+ // key", verified 2026-09-22), so login succeeds while a slot is idle and
8
+ // inference needs one. Keys are lane-scoped `sk-...` bearer tokens issued
9
+ // from the dashboard.
10
+ // Key validation probes the non-billable `GET /v1/models`: it answers 401
11
+ // for a missing, malformed, or unknown key (verified 2026-09-21), so a bad
12
+ // key is rejected without spending.
13
+ auth "singularityapi-tech" {
14
+ name "SingularityAPI Reserved Lanes"
15
+ env "SINGULARITYAPI_TECH_API_KEY"
16
+ login "api-key" {
17
+ auth-url "https://app.singularityapi.tech/compute/billing"
18
+ instructions "Create a key from the SingularityAPI lanes dashboard, then paste it here"
19
+ prompt "Paste your SingularityAPI lanes key" placeholder="sk-..."
20
+ normalize "strip-bearer"
21
+ validate "models-endpoint" label="SingularityAPI Reserved Lanes" url="https://api.singularityapi.tech/v1/models"
22
+ }
23
+ }
@@ -13,4 +13,7 @@ class "gpt-oss" {
13
13
  on "venice" "vercel-ai-gateway" {
14
14
  thinking-efforts "minimal" "low" "medium" "high" "xhigh"
15
15
  }
16
+ on "google-antigravity" "google-gemini-cli" {
17
+ supports-function-part-id #true
18
+ }
16
19
  }
@@ -5,7 +5,7 @@ class "xai" {
5
5
  // on both the API and OAuth surfaces; the multiplier form tracks
6
6
  // stencil.so price updates. Zero-cost subscription rows carry no tier.
7
7
  on "xai" "xai-oauth" {
8
- models "grok-4.3" "grok-4.5" "grok-4.6" "grok-build-0.1" "grok-4.20*" {
8
+ models "grok-4.3" "grok-4.5" "grok-4.6" "grok-4.7" "grok-build-0.1" "grok-4.20*" {
9
9
  long-context-cost {
10
10
  input-threshold 200000
11
11
  input-threshold-inclusive #true
@@ -26,10 +26,10 @@ class "xai" {
26
26
  }
27
27
  }
28
28
  }
29
- // First-party xhigh-capable SKUs (grok-4.6, multi-agent) advertise xhigh.
29
+ // First-party xhigh-capable SKUs (grok-4.6, grok-4.7, multi-agent) advertise xhigh.
30
30
  on "xai" "xai-oauth" {
31
31
  family "grok" {
32
- models "grok-4.6*" "grok-4.20-multi-agent*" {
32
+ models "grok-4.6*" "grok-4.7*" "grok-4.20-multi-agent*" {
33
33
  thinking-efforts "minimal" "low" "medium" "high" "xhigh"
34
34
  }
35
35
  }
@@ -1,7 +1,7 @@
1
1
  // Provider-wire compat for "amazon-bedrock"; regenerated from the frozen census using deployment contract selectors.
2
2
 
3
3
  provider "amazon-bedrock" {
4
- default-model "us.anthropic.claude-opus-4-8"
4
+ default-model "us.anthropic.claude-opus-5-5"
5
5
 
6
6
  // The Converse assembler positions content blocks by wire index
7
7
  // (`amazon-bedrock.ts`), so a block can land above text already rendered.
@@ -1,7 +1,7 @@
1
1
  // Provider-wire compat for "anthropic"; regenerated from the frozen census using deployment contract selectors.
2
2
 
3
3
  provider "anthropic" {
4
- default-model "claude-opus-4-8"
4
+ default-model "claude-opus-5-5"
5
5
  env "ANTHROPIC_API_KEY"
6
6
  discovery label="Anthropic"
7
7
  web-search "anthropic"
@@ -1,7 +1,7 @@
1
1
  // Provider-wire compat for "cloudflare-ai-gateway"; regenerated from the frozen census using deployment contract selectors.
2
2
 
3
3
  provider "cloudflare-ai-gateway" {
4
- default-model "anthropic/claude-opus-4-8"
4
+ default-model "anthropic/claude-opus-5"
5
5
  env "CLOUDFLARE_AI_GATEWAY_API_KEY"
6
6
  discovery label="Cloudflare AI Gateway"
7
7
 
@@ -9,7 +9,7 @@
9
9
  // dials to a few further ids — MiniMaxAI/MiniMax-M3 and meta/muse-spark-1.3's
10
10
  // `max` — which stay out of this change.
11
11
  provider "commandcode" {
12
- default-model "claude-sonnet-4-6"
12
+ default-model "claude-sonnet-5"
13
13
  env "COMMAND_CODE_API_KEY" "COMMANDCODE_API_KEY"
14
14
  allow-unauthenticated #true
15
15
  dynamic-models-authoritative #true
@@ -1,7 +1,7 @@
1
1
  // Provider-wire compat for "cursor"; regenerated from the frozen census using deployment contract selectors.
2
2
 
3
3
  provider "cursor" {
4
- default-model "claude-4.6-opus-high"
4
+ default-model "claude-opus-5-high"
5
5
  env "CURSOR_ACCESS_TOKEN"
6
6
  discovery label="Cursor" oauth-provider="cursor" {
7
7
  env "CURSOR_API_KEY"
@@ -17,6 +17,11 @@ provider "google-antigravity" {
17
17
  }
18
18
  }
19
19
 
20
+ // Routed wire profiles overwrite caller caps with fixed output limits.
21
+ // Conservatively reject requested bounds for this provider, including
22
+ // logical ids whose effort routing selects a profiled wire id later.
23
+ preserves-max-output-tokens #false
24
+
20
25
  class "anthropic" {
21
26
  family "opus" {
22
27
  thinking-mode "budget"
@@ -1,7 +1,7 @@
1
1
  // Provider-wire compat for "kilo"; regenerated from the frozen census using deployment contract selectors.
2
2
 
3
3
  provider "kilo" {
4
- default-model "anthropic/claude-opus-4.8"
4
+ default-model "anthropic/claude-opus-5"
5
5
  env "KILO_API_KEY"
6
6
  discovery label="Kilo Gateway" allow-unauthenticated=#true
7
7
 
@@ -1,7 +1,7 @@
1
1
  // Catalog entry for "litellm"; no deployment-contract compat rules are needed.
2
2
 
3
3
  provider "litellm" {
4
- default-model "claude-opus-4-8"
4
+ default-model "claude-opus-5-5"
5
5
  env "LITELLM_API_KEY"
6
6
  discovery label="LiteLLM" allow-unauthenticated=#true
7
7
  }
@@ -0,0 +1,4 @@
1
+ // Cursor always exposes server-owned native operations, even with an empty tool catalog.
2
+ on-api "cursor-agent" {
3
+ requires-native-tools #true
4
+ }
@@ -4,7 +4,9 @@ provider "openai" {
4
4
  default-model "gpt-5.5"
5
5
  env "OPENAI_API_KEY"
6
6
  kind-apis {
7
+ embedding "openai-embeddings"
7
8
  image "openai-responses"
9
+ stt "openai-transcriptions"
8
10
  }
9
11
 
10
12
  // Daybreak models are approval-gated first-party Responses models that are
@@ -33,6 +35,62 @@ provider "openai" {
33
35
  cost input=12.5 output=75 cache-read=1.25 cache-write=15.625
34
36
  limits context=400000 max-tokens=128000
35
37
  }
38
+
39
+ // Catalog cost fields are per 1M tokens: GPT transcribers map documented
40
+ // audio-input/output-token rates directly. Whisper's $0.006/min duration
41
+ // tariff has no token-cost representation, so it remains zero and the
42
+ // transcription response's provider-reported usage/cost is authoritative.
43
+ model "whisper-1" name="Whisper 1" api="openai-transcriptions" base-url="https://api.openai.com/v1" {
44
+ reasoning #false
45
+ input "text"
46
+ cost input=0 output=0 cache-read=0 cache-write=0
47
+ limits
48
+ supports-tools #false
49
+ }
50
+ model "gpt-4o-transcribe" name="GPT-4o Transcribe" api="openai-transcriptions" base-url="https://api.openai.com/v1" {
51
+ reasoning #false
52
+ input "text"
53
+ cost input=2.5 output=10 cache-read=0 cache-write=0
54
+ limits context=16000 max-tokens=2000
55
+ supports-tools #false
56
+ }
57
+ model "gpt-4o-mini-transcribe" name="GPT-4o Mini Transcribe" api="openai-transcriptions" base-url="https://api.openai.com/v1" {
58
+ reasoning #false
59
+ input "text"
60
+ cost input=1.25 output=5 cache-read=0 cache-write=0
61
+ limits context=16000 max-tokens=2000
62
+ supports-tools #false
63
+ }
64
+ // OpenAI publishes embedding prices per million input tokens; embedding
65
+ // responses have no output-token charge.
66
+ model "text-embedding-3-small" name="Text Embedding 3 Small" api="openai-embeddings" base-url="https://api.openai.com/v1" {
67
+ reasoning #false
68
+ input "text"
69
+ cost input=0.02 output=0 cache-read=0 cache-write=0
70
+ limits context=8192
71
+ supports-tools #false
72
+ }
73
+ model "text-embedding-3-large" name="Text Embedding 3 Large" api="openai-embeddings" base-url="https://api.openai.com/v1" {
74
+ reasoning #false
75
+ input "text"
76
+ cost input=0.13 output=0 cache-read=0 cache-write=0
77
+ limits context=8192
78
+ supports-tools #false
79
+ }
80
+ model "text-embedding-ada-002" name="Text Embedding Ada 002" api="openai-embeddings" base-url="https://api.openai.com/v1" {
81
+ reasoning #false
82
+ input "text"
83
+ cost input=0.1 output=0 cache-read=0 cache-write=0
84
+ limits context=8192
85
+ supports-tools #false
86
+ }
87
+ }
88
+
89
+ models "whisper-1" "gpt-4o-transcribe" "gpt-4o-mini-transcribe" {
90
+ kind "stt"
91
+ }
92
+ models "text-embedding-3-small" "text-embedding-3-large" "text-embedding-ada-002" {
93
+ kind "embedding"
36
94
  }
37
95
 
38
96
  // Replaces the strict-mode provider whitelist entry.
@@ -1,7 +1,7 @@
1
1
  // Provider-wire compat for "opencode-zen"; regenerated from the frozen census using deployment contract selectors.
2
2
 
3
3
  provider "opencode-zen" {
4
- default-model "claude-opus-4-8"
4
+ default-model "claude-opus-5"
5
5
  env "OPENCODE_API_KEY"
6
6
  dynamic-models-authoritative #true
7
7
 
@@ -5,7 +5,12 @@ provider "openrouter" {
5
5
  env "OPENROUTER_API_KEY"
6
6
  discovery label="OpenRouter" allow-unauthenticated=#true
7
7
  kind-apis {
8
+ embedding "openai-embeddings"
8
9
  image "openrouter-images"
10
+ rerank "openrouter-rerank"
11
+ video "openrouter-video"
12
+ tts "openai-speech"
13
+ stt "openai-transcriptions"
9
14
  }
10
15
  web-search "openrouter"
11
16
 
@@ -19,10 +24,113 @@ provider "openrouter" {
19
24
  cost input=0.042 output=0 cache-read=0 cache-write=0
20
25
  limits context=32000 max-tokens=28800
21
26
  }
27
+
28
+ // OpenRouter's STT roster mixes per-token and duration-based prices.
29
+ // Token-priced GPT rows map per-token rates to catalog per-million costs;
30
+ // duration-priced rows remain zero because ModelCost has no seconds axis.
31
+ model "openai/whisper-1" name="OpenAI: Whisper 1" api="openai-transcriptions" base-url="https://openrouter.ai/api/v1" {
32
+ reasoning #false
33
+ input "text"
34
+ cost input=0 output=0 cache-read=0 cache-write=0
35
+ limits
36
+ supports-tools #false
37
+ }
38
+ model "openai/whisper-large-v3" name="OpenAI: Whisper Large V3" api="openai-transcriptions" base-url="https://openrouter.ai/api/v1" {
39
+ reasoning #false
40
+ input "text"
41
+ cost input=0 output=0 cache-read=0 cache-write=0
42
+ limits
43
+ supports-tools #false
44
+ }
45
+ model "openai/gpt-4o-transcribe" name="OpenAI: GPT-4o Transcribe" api="openai-transcriptions" base-url="https://openrouter.ai/api/v1" {
46
+ reasoning #false
47
+ input "text"
48
+ cost input=2.5 output=10 cache-read=0 cache-write=0
49
+ limits context=128000 max-tokens=115200
50
+ supports-tools #false
51
+ }
52
+ model "microsoft/mai-transcribe-1.5" name="Microsoft AI: MAI-Transcribe 1.5" api="openai-transcriptions" base-url="https://openrouter.ai/api/v1" {
53
+ reasoning #false
54
+ input "text"
55
+ cost input=0 output=0 cache-read=0 cache-write=0
56
+ limits
57
+ supports-tools #false
58
+ }
59
+ model "microsoft/mai-transcribe-2" name="Microsoft AI: MAI-Transcribe 2" api="openai-transcriptions" base-url="https://openrouter.ai/api/v1" {
60
+ reasoning #false
61
+ input "text"
62
+ cost input=0 output=0 cache-read=0 cache-write=0
63
+ limits
64
+ supports-tools #false
65
+ }
66
+
67
+ // OpenRouter bills reranking per 1,000 searches, which has no catalog cost
68
+ // axis. Keep token costs at zero; the provider-reported response cost is authoritative.
69
+ model "cohere/rerank-v3.5" name="Cohere: Rerank v3.5" api="openrouter-rerank" base-url="https://openrouter.ai/api/v1" {
70
+ reasoning #false
71
+ input "text"
72
+ cost input=0 output=0 cache-read=0 cache-write=0
73
+ limits context=4096 max-tokens=3686
74
+ supports-tools #false
75
+ }
76
+ // Bundled fallbacks keep the gateway useful offline; live
77
+ // `/embeddings/models` discovery refreshes this roster and its per-token
78
+ // pricing. Catalog token costs are per million input tokens.
79
+ model "openai/text-embedding-3-small" name="OpenAI: Text Embedding 3 Small" api="openai-embeddings" base-url="https://openrouter.ai/api/v1" {
80
+ reasoning #false
81
+ input "text"
82
+ cost input=0.02 output=0 cache-read=0 cache-write=0
83
+ limits context=8192
84
+ supports-tools #false
85
+ }
86
+ model "qwen/qwen3-embedding-8b" name="Qwen: Qwen3 Embedding 8B" api="openai-embeddings" base-url="https://openrouter.ai/api/v1" {
87
+ reasoning #false
88
+ input "text"
89
+ cost input=0.01 output=0 cache-read=0 cache-write=0
90
+ limits context=32768
91
+ supports-tools #false
92
+ }
93
+ // OpenRouter bills generated video by output second and resolution/SKU,
94
+ // which ModelCost cannot represent. Keep token costs at zero; poll-reported
95
+ // cost is authoritative. Live `/videos/models` discovery refreshes the roster.
96
+ model "google/veo-3.1" name="Google: Veo 3.1" api="openrouter-video" base-url="https://openrouter.ai/api/v1" {
97
+ reasoning #false
98
+ input "text" "image"
99
+ cost input=0 output=0 cache-read=0 cache-write=0
100
+ limits
101
+ supports-tools #false
102
+ }
103
+ model "minimax/hailuo-3" name="MiniMax: H3" api="openrouter-video" base-url="https://openrouter.ai/api/v1" {
104
+ reasoning #false
105
+ input "text" "image"
106
+ cost input=0 output=0 cache-read=0 cache-write=0
107
+ limits
108
+ supports-tools #false
109
+ }
110
+ model "alibaba/wan-2.7" name="Alibaba: Wan 2.7" api="openrouter-video" base-url="https://openrouter.ai/api/v1" {
111
+ reasoning #false
112
+ input "text" "image"
113
+ cost input=0 output=0 cache-read=0 cache-write=0
114
+ limits
115
+ supports-tools #false
116
+ }
22
117
  }
23
118
  models "~typesafe/*" "typesafe/*" {
24
119
  kind "judge"
25
120
  }
121
+ models "cohere/rerank-v3.5" {
122
+ kind "rerank"
123
+ }
124
+ models "openai/text-embedding-3-small" "qwen/qwen3-embedding-8b" {
125
+ kind "embedding"
126
+ }
127
+ models "google/veo-3.1" "minimax/hailuo-3" "alibaba/wan-2.7" {
128
+ kind "video"
129
+ }
130
+ models "openai/whisper-1" "openai/whisper-large-v3" "openai/gpt-4o-transcribe" \
131
+ "microsoft/mai-transcribe-1.5" "microsoft/mai-transcribe-2" {
132
+ kind "stt"
133
+ }
26
134
 
27
135
  // Replaces the OpenRouter provider wire-model-id dispatch branch.
28
136
  wire-model-id-mode "openrouter"
@@ -0,0 +1,4 @@
1
+ // These transports do not encode caller output limits, regardless of provider or model name.
2
+ on-api "openai-codex-responses" "cursor-agent" "gitlab-duo-agent" {
3
+ omit-max-output-tokens #true
4
+ }
@@ -0,0 +1,92 @@
1
+ // SingularityAPI universal inference gateway (api.singularityapi.dev):
2
+ // one OpenAI-compatible endpoint for 300+ models (DeepSeek, Kimi, GLM,
3
+ // frontier flagships), `sapi_...` bearer keys issued from the dashboard at
4
+ // app.singularityapi.dev. `GET /v1/models` publishes each row's per-endpoint
5
+ // capabilities — context window, max/default output tokens, and per-million
6
+ // 12-decimal pricing strings — with `cache-control: no-store`, so discovery
7
+ // reads limits and tariffs live and no rows are frozen here.
8
+ //
9
+ // Deliberately no `discovery` node: live discovery needs a user credential,
10
+ // and enrolling would freeze one account's snapshot into models.json on every
11
+ // credential-less regen. The provider stays runtime-only and
12
+ // `dynamic-models-authoritative` prunes stale rows.
13
+ // The vendor's second product — slot-reserved DeepSeek lanes on
14
+ // api.singularityapi.tech — lives in `singularityapi-tech`: separate provider
15
+ // id because the two gateways publish conflicting effort ladders (`max`
16
+ // passes there and 400s here; `medium` is the reverse, both measured live
17
+ // 2026-09-22) and neither key works on the other host.
18
+ provider "singularityapi-dev" {
19
+ default-model "deepseek-v4-flash"
20
+ env "SINGULARITYAPI_DEV_API_KEY"
21
+ dynamic-models-authoritative #true
22
+
23
+ // Gateway-wide request shape, from the OpenAI-compatibility contract
24
+ // (docs.singularityapi.dev/get-started/open-ai-compatibility): chat
25
+ // completions accept `max_tokens` and `max_completion_tokens`
26
+ // interchangeably; the gateway normalizes to the model's canonical
27
+ // field. Unknown/reserved fields 400 instead of dropping, duplicate
28
+ // JSON keys and NaN/Infinity 400, context overflow 400s before spend.
29
+ // Rows the `models` rules below do not review inherit exactly this
30
+ // shape instead of the openai-completions default, because the roster
31
+ // is account-scoped and unreviewed model ids are expected.
32
+ max-tokens-field "max_tokens"
33
+
34
+ // Reviewed lane rules for the DeepSeek rows the gateway publishes,
35
+ // keyed as case-insensitive globs (`models` exact selectors compare the
36
+ // raw id verbatim while the compiler lowercases them, so exact rules
37
+ // can never match mixed-case wire ids). DeepSeek V4 Flash rows classify
38
+ // deepseek/flash by taxonomy but publish no reasoning metadata, so the
39
+ // upgrade rule owns the measured low/medium/high ladder; reasoning arrives
40
+ // as top-level `reasoning_content` on messages and streamed deltas, and
41
+ // `none` forces it off. V4 Pro the same, with the Pro ladder.
42
+ //
43
+ // Ladder measured against the live gateway 2026-09-22: `none`, `minimal`,
44
+ // `low`, `medium`, `high` pass admission while `xhigh`, `max`, integer and
45
+ // unknown efforts answer 400 `invalid_request` — admission validation runs
46
+ // before the credit reservation, so the probe sorted accepted from rejected
47
+ // at 402 vs 400 without spending a cent. `max` in particular is a
48
+ // reserve-lane-only tier (`singularityapi-tech`); sending it here turned
49
+ // every DeepSeek request into a 400.
50
+ models "*deepseek-v4-flash*" {
51
+ thinking-upgrade-neutral #true
52
+ max-tokens-field "max_tokens"
53
+ thinking-efforts "low" "medium" "high"
54
+ reasoning-disable-mode "none-effort"
55
+ reasoning-content-field "reasoning_content"
56
+ }
57
+ models "*deepseek-v4-pro*" {
58
+ thinking-upgrade-neutral #true
59
+ max-tokens-field "max_tokens"
60
+ thinking-efforts "low" "medium" "high"
61
+ reasoning-disable-mode "none-effort"
62
+ reasoning-content-field "reasoning_content"
63
+ }
64
+ // Responses-capable flagships (gpt-5.6-sol/terra/luna): five-tier
65
+ // low..max ladder with the wire-exact off switch, matching the
66
+ // first-party GPT-5.6 rows. `thinking-upgrade-neutral` is what makes the
67
+ // ladder real: the wire publishes no reasoning metadata, so without it the
68
+ // rows stay non-reasoning and omp sends no `reasoning_effort` at all —
69
+ // which the gateway rejects (400 from upstream) on chat completions
70
+ // whenever `tools` are present, exactly the case a coding agent hits.
71
+ models "gpt-5.6-sol" "gpt-5.6-terra" "gpt-5.6-luna" {
72
+ thinking-upgrade-neutral #true
73
+ thinking-efforts "low" "medium" "high" "xhigh" "max"
74
+ reasoning-disable-mode "none-effort"
75
+ }
76
+ // Gateway image models serve POST /v1/images/generations, never billed
77
+ // by tokens: FLUX per megapixel, GPT Image per image. The `kind` rules
78
+ // keep them out of chat; `mapSingularityApiModel` reads the same rows'
79
+ // `capabilities` and assigns the `openai-images` transport, so a new
80
+ // image id the roster adds works without a rule edit here.
81
+ models "flux-1-schnell" "flux-pro-1.1" {
82
+ kind "image"
83
+ }
84
+ models "gpt-image-2" "gpt-image-1.5" {
85
+ kind "image"
86
+ }
87
+ // The gateway's DeepSeek rows reject tool_choice: the API defaults to
88
+ // auto when tools exist. Matches the first-party DeepSeek transport.
89
+ models "*deepseek*" {
90
+ supports-tool-choice #false
91
+ }
92
+ }