dsh-llm-omp-transports 0.0.0-stage → 0.2.2
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.
- package/README.md +147 -2
- package/bundle/cordis.patch.yml +6 -0
- package/lib/adapter.d.ts +64 -0
- package/lib/adapter.js +167 -0
- package/lib/adapter.js.map +1 -0
- package/lib/catalog/cursor.d.ts +29 -0
- package/lib/catalog/cursor.js +3954 -0
- package/lib/catalog/cursor.js.map +1 -0
- package/lib/cursor/auth.d.ts +127 -0
- package/lib/cursor/auth.js +299 -0
- package/lib/cursor/auth.js.map +1 -0
- package/lib/cursor/credentials.d.ts +52 -0
- package/lib/cursor/credentials.js +111 -0
- package/lib/cursor/credentials.js.map +1 -0
- package/lib/index.d.ts +135 -0
- package/lib/index.js +118 -0
- package/lib/index.js.map +1 -0
- package/lib/omp/cursor.mjs +22172 -0
- package/lib/omp.d.ts +232 -0
- package/lib/omp.js +21 -0
- package/lib/omp.js.map +1 -0
- package/lib/projection.d.ts +69 -0
- package/lib/projection.js +582 -0
- package/lib/projection.js.map +1 -0
- package/package.json +69 -4
package/README.md
CHANGED
|
@@ -1,3 +1,148 @@
|
|
|
1
|
-
#
|
|
1
|
+
# dsh-llm-omp-transports
|
|
2
2
|
|
|
3
|
-
|
|
3
|
+
A DeepSeek Harness LLM transport component for providers whose wire protocols
|
|
4
|
+
the vendored `llm-pi-ai` does not speak. It is published from this repository
|
|
5
|
+
as `dsh-llm-omp-transports` and installed as a dependency of
|
|
6
|
+
`dsh-keys-manager`: installing the Keys Manager plugin brings this component,
|
|
7
|
+
and the plugin page lists both bundle components
|
|
8
|
+
(`dsh-keys-manager` and `llm-omp-transports`).
|
|
9
|
+
|
|
10
|
+
| Fact | Value |
|
|
11
|
+
|---|---|
|
|
12
|
+
| npm package | `dsh-llm-omp-transports` |
|
|
13
|
+
| Plugin id | `llm-omp-transports` |
|
|
14
|
+
| Route | `cursor` (first provider; the seam is provider-generic) |
|
|
15
|
+
| Credential scope | `llm-omp-transports/<provider>`, today `llm-omp-transports/cursor` |
|
|
16
|
+
| Runtime | Node 24 (the bundle imports Node builtins only) |
|
|
17
|
+
| License | MIT |
|
|
18
|
+
|
|
19
|
+
The plugin registers its own route on the DSH `llm` seam, so it depends on no
|
|
20
|
+
upstream DSH change. `@oh-my-pi/pi-ai` and `@oh-my-pi/pi-catalog` are used at
|
|
21
|
+
**build time only**: the build inlines the pinned omp Cursor transport into one
|
|
22
|
+
ESM artifact (`lib/omp/cursor.mjs`), and the published package imports nothing
|
|
23
|
+
from `@oh-my-pi/*` or `bun:*` at runtime.
|
|
24
|
+
|
|
25
|
+
## Cursor support status
|
|
26
|
+
|
|
27
|
+
- **Text streaming** — yes. Assistant text and usage are projected onto DSH's
|
|
28
|
+
`StreamChunk` stream.
|
|
29
|
+
- **Reasoning streaming** — yes, with the catalog's effort routing. The
|
|
30
|
+
selected effort becomes the routed wire model id; an effort the model does
|
|
31
|
+
not advertise is refused with `UNSUPPORTED_REASONING_EFFORT`.
|
|
32
|
+
- **Tool-call handoff** — yes, through DSH's tool loop. Cursor's server drives
|
|
33
|
+
execution over its exec channel, so the transport runs in external-executor
|
|
34
|
+
mode: an unhandled MCP call is emitted as an unresolved tool call and
|
|
35
|
+
answered with a handoff, DSH runs the tool, and the next request replays the
|
|
36
|
+
result from history. The adapter never executes a tool itself.
|
|
37
|
+
- **Sign-in and refresh** — yes. The package registers the
|
|
38
|
+
`llm-omp-transports/cursor` authorization flow (a browser login page plus a
|
|
39
|
+
poll, no loopback callback and no device code) and refreshes an expiring
|
|
40
|
+
grant under the credential store's per-key lock. The Keys Manager Web page's
|
|
41
|
+
**Transport accounts** section is the surface that starts the flow.
|
|
42
|
+
- **Models** — from the pinned catalog: the Cursor slice of
|
|
43
|
+
`@oh-my-pi/pi-catalog@18.12.3` (123 rows) is generated into
|
|
44
|
+
`src/catalog/cursor.ts` and served without a network call.
|
|
45
|
+
- **Route** — `cursor`, declared configurable so the Models page has a profile
|
|
46
|
+
entry for it.
|
|
47
|
+
- **Images** — not yet. The route advertises text-only input and refuses image
|
|
48
|
+
blocks with `CONTENT_UNSUPPORTED`; see [known limits](docs/known-limits.md).
|
|
49
|
+
|
|
50
|
+
## Hard constraints
|
|
51
|
+
|
|
52
|
+
- **Pinned, build-time-only omp.** `@oh-my-pi/pi-ai` and `@oh-my-pi/pi-catalog`
|
|
53
|
+
are pinned to `18.12.3` and declared as devDependencies. No runtime package
|
|
54
|
+
may import them: `tests/build.test.ts` checks that every static import of the
|
|
55
|
+
shipped artifact is a Node builtin.
|
|
56
|
+
- **Node 24 load.** The artifact is imported through a plain Node ESM loader
|
|
57
|
+
with no Bun global present, and must expose `streamCursor`. The Bun and
|
|
58
|
+
`@oh-my-pi/pi-utils` surface the bundled graph reaches is covered by the
|
|
59
|
+
shims in `scripts/omp-shim/`; a missing shim symbol or a new shim category
|
|
60
|
+
fails the build.
|
|
61
|
+
- **Drift gate.** `scripts/omp-manifest.json` records the pinned versions, the
|
|
62
|
+
measured artifact, the shim surface and the hashes of every source the
|
|
63
|
+
transport depends on, plus the shim symbols the esbuild graph actually
|
|
64
|
+
reaches. `tests/build.test.ts` re-checks all of it, and CI asserts the
|
|
65
|
+
committed manifest is unchanged after a build, so an omp bump that changes
|
|
66
|
+
the contract shows up as a reviewable manifest diff before it can reach a
|
|
67
|
+
request.
|
|
68
|
+
- **Generated catalog.** The Cursor model table is generated from the pinned
|
|
69
|
+
catalog and is not hand-edited. An omp or catalog bump requires
|
|
70
|
+
`pnpm -C packages/llm-omp run generate:catalog`.
|
|
71
|
+
|
|
72
|
+
## Limits and risks
|
|
73
|
+
|
|
74
|
+
- **Unofficial Cursor client.** The transport reuses Cursor's vendor-internal
|
|
75
|
+
OAuth client id and announces a released CLI build through the
|
|
76
|
+
`x-cursor-client-version` / `x-cursor-client-type` request identity. The MIT
|
|
77
|
+
license covers the code, not the service, so relying on this client carries a
|
|
78
|
+
terms-of-service (ToS) risk. If Cursor gates non-IDE clients (a `401`/`403`
|
|
79
|
+
on `Run` with a valid account), this transport stops until the product
|
|
80
|
+
decision recorded as stop condition **S4**.
|
|
81
|
+
- **Real endpoints unverified.** The login, poll, refresh and agent endpoint
|
|
82
|
+
shapes are ported from the pinned omp sources; this repository's tests replay
|
|
83
|
+
recorded fixtures and never call Cursor, so live behavior is unverified until
|
|
84
|
+
it is exercised against a real account.
|
|
85
|
+
- **In-process checkpoint cache.** Per-conversation checkpoints live in a
|
|
86
|
+
module-level, in-process LRU (128 conversations) inside the bundled omp
|
|
87
|
+
transport. Nothing is persisted: an evicted or lost checkpoint rebuilds from
|
|
88
|
+
the request history, exactly like the first request after a restart, and a
|
|
89
|
+
multi-step tool turn must replay its history.
|
|
90
|
+
- **Image input is advertised as text-only.** Forwarding is future work; until
|
|
91
|
+
it lands the projection refuses non-text blocks instead of silently dropping
|
|
92
|
+
them. 100 of the pinned catalog's 123 rows claim image support but are
|
|
93
|
+
advertised text-only.
|
|
94
|
+
- **Tool handoff uses DSH's external-executor mode.** A turn that needs a tool
|
|
95
|
+
stops at the handoff; the result is only replayed on the follow-up request.
|
|
96
|
+
Tool declarations travel as MCP definitions, and `toolHistory` is accepted
|
|
97
|
+
but cannot be replayed (the active tool set is the projection).
|
|
98
|
+
- **Only MCP calls are handed off.** Cursor-native exec frames (`read`, `shell`,
|
|
99
|
+
`write`, `delete`, `grep`, `ls`, `diagnostics`, streamed edits) are answered
|
|
100
|
+
by the transport with `Tool not available` and are **not** executed by DSH
|
|
101
|
+
(live reachability unverified).
|
|
102
|
+
- **Advisory request knobs are ignored.** Cursor's agent protocol has no field
|
|
103
|
+
for an output cap, sampling temperature, stop sequences or an auxiliary-call
|
|
104
|
+
purpose; DSH's `maxTokens`, `temperature`, `stop` and `purpose` never reach
|
|
105
|
+
the wire, and Cursor applies the catalog output limit server-side.
|
|
106
|
+
|
|
107
|
+
## Develop and test
|
|
108
|
+
|
|
109
|
+
```sh
|
|
110
|
+
pnpm -C packages/llm-omp typecheck
|
|
111
|
+
pnpm -C packages/llm-omp build
|
|
112
|
+
pnpm -C packages/llm-omp test
|
|
113
|
+
pnpm -C packages/llm-omp run generate:catalog
|
|
114
|
+
```
|
|
115
|
+
|
|
116
|
+
`build` bundles the pinned omp graph from `scripts/omp-entry.ts` into
|
|
117
|
+
`lib/omp/cursor.mjs` and rewrites `scripts/omp-manifest.json`; run it before
|
|
118
|
+
`test` after a pin or shim change. CI runs the same sequence and then fails if
|
|
119
|
+
the committed manifest drifted.
|
|
120
|
+
|
|
121
|
+
The install proof lives at the repository root and needs `pnpm` and `dsh` on
|
|
122
|
+
`PATH`:
|
|
123
|
+
|
|
124
|
+
```sh
|
|
125
|
+
node scripts/verify-install.mjs
|
|
126
|
+
```
|
|
127
|
+
|
|
128
|
+
It packs both packages, installs the root tarball into a fresh DSH profile,
|
|
129
|
+
and asserts that the composed profile carries both loader rows
|
|
130
|
+
(`dsh-keys-manager` and `llm-omp-transports`). It does not exercise the
|
|
131
|
+
plugin-manager UI or any Cursor network behavior.
|
|
132
|
+
|
|
133
|
+
## Release
|
|
134
|
+
|
|
135
|
+
This package is released from the same release PR and carries the same version
|
|
136
|
+
as `dsh-keys-manager`; the root `CHANGELOG.md` and its generated sections cover
|
|
137
|
+
the root package only. A release-prep run writes one version to both
|
|
138
|
+
`package.json` files, and the Release workflow publishes both and pushes the
|
|
139
|
+
`dsh-llm-omp-transports@<version>` tag.
|
|
140
|
+
The root [release docs](../../docs/release.md) describe the full flow.
|
|
141
|
+
|
|
142
|
+
Package documentation is English-only; the root `README.md` /
|
|
143
|
+
`README.zh-CN.md` and the root `docs/*.zh-CN.md` files carry the bilingual
|
|
144
|
+
plugin surface.
|
|
145
|
+
|
|
146
|
+
## License
|
|
147
|
+
|
|
148
|
+
Released under the [MIT License](../../LICENSE).
|
|
@@ -0,0 +1,6 @@
|
|
|
1
|
+
# Mounts the llm-omp-transports transport plugin when this package is installed on its
|
|
2
|
+
# own. It owns the `cursor` (later `devin`, …) LLM routes and the
|
|
3
|
+
# `llm-omp-transports/<provider>` credential scope.
|
|
4
|
+
- insert:
|
|
5
|
+
- id: llm-omp-transports
|
|
6
|
+
name: 'dsh-llm-omp-transports'
|
package/lib/adapter.d.ts
ADDED
|
@@ -0,0 +1,64 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Adapter for the omp-owned `cursor` route.
|
|
3
|
+
*
|
|
4
|
+
* The route speaks Cursor's own agent protocol (`agent.v1.AgentService/Run`
|
|
5
|
+
* over HTTP/2) through the omp build artifact in `lib/omp/cursor.mjs`. The
|
|
6
|
+
* transport is injected rather than imported so this module stays free of the
|
|
7
|
+
* 14 MB build artifact and tests can replay recorded event scripts. The plugin
|
|
8
|
+
* wires the bundled `streamCursor` at registration and the credential seam
|
|
9
|
+
* provides {@link OmpCursorAdapterConfig.access}, which refreshes an expiring
|
|
10
|
+
* grant under the store's lock before it answers.
|
|
11
|
+
*
|
|
12
|
+
* The catalog is the generated `src/catalog/cursor.ts`, so `listModels` and
|
|
13
|
+
* `resolveModel` answer without a network call and carry the transport flags the
|
|
14
|
+
* projection needs (effort routing, max mode, glyph tokenization).
|
|
15
|
+
*
|
|
16
|
+
* @module dsh-llm-omp-transports/adapter
|
|
17
|
+
*/
|
|
18
|
+
import { LlmAdapter } from '@deepseek-ai/dsh-llm';
|
|
19
|
+
import type { GenerateOptions, LlmModelInfo, LlmProviderInfo, LlmResolvedModelInfo, StreamChunk } from '@deepseek-ai/dsh-llm';
|
|
20
|
+
import type { OmpCursorTransport } from './omp.js';
|
|
21
|
+
/** The provider route this adapter owns. */
|
|
22
|
+
export declare const CURSOR_ROUTE = "cursor";
|
|
23
|
+
/** Machine code for a model id the generated catalog does not contain. */
|
|
24
|
+
export declare const UNKNOWN_MODEL = "UNKNOWN_MODEL";
|
|
25
|
+
/** Machine code for a provider route this adapter does not serve. */
|
|
26
|
+
export declare const UNKNOWN_PROVIDER = "UNKNOWN_PROVIDER";
|
|
27
|
+
/** What the adapter needs from its host plugin. */
|
|
28
|
+
export interface OmpCursorAdapterConfig {
|
|
29
|
+
/**
|
|
30
|
+
* Resolve the Cursor bearer token for one request.
|
|
31
|
+
*
|
|
32
|
+
* @remarks
|
|
33
|
+
* Asynchronous because it reads and refreshes the `llm-omp-transports/cursor`
|
|
34
|
+
* credential through the credentials seam. The request signal is forwarded
|
|
35
|
+
* so an aborted turn can abandon a refresh instead of writing it late. Tests
|
|
36
|
+
* inject a fake.
|
|
37
|
+
*/
|
|
38
|
+
access: (signal?: AbortSignal) => Promise<string>;
|
|
39
|
+
/**
|
|
40
|
+
* The omp transport, normally the `streamCursor` export of
|
|
41
|
+
* `lib/omp/cursor.mjs`. The seam tests drive it with recorded event scripts.
|
|
42
|
+
*/
|
|
43
|
+
transport: OmpCursorTransport;
|
|
44
|
+
}
|
|
45
|
+
/** The DSH llm adapter for every route this plugin's omp transport serves. */
|
|
46
|
+
export declare class OmpCursorAdapter extends LlmAdapter {
|
|
47
|
+
private readonly config;
|
|
48
|
+
constructor(config: OmpCursorAdapterConfig);
|
|
49
|
+
/**
|
|
50
|
+
* Describe the route.
|
|
51
|
+
*
|
|
52
|
+
* @remarks
|
|
53
|
+
* Cursor's agent protocol takes no client-side output cap, sampling
|
|
54
|
+
* temperature, stop sequence or auxiliary-call purpose: the wire carries no
|
|
55
|
+
* field for any of them, so the projection ignores those `GenerateOptions`
|
|
56
|
+
* values instead of forwarding them. Cursor applies the catalog `maxTokens`
|
|
57
|
+
* limit server-side.
|
|
58
|
+
*/
|
|
59
|
+
providerInfo(provider: string): LlmProviderInfo;
|
|
60
|
+
listModels(provider: string): Promise<readonly LlmModelInfo[]>;
|
|
61
|
+
resolveModel(provider: string, model: string): Promise<LlmResolvedModelInfo>;
|
|
62
|
+
stream(options: GenerateOptions): AsyncIterable<StreamChunk>;
|
|
63
|
+
private call;
|
|
64
|
+
}
|
package/lib/adapter.js
ADDED
|
@@ -0,0 +1,167 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Adapter for the omp-owned `cursor` route.
|
|
3
|
+
*
|
|
4
|
+
* The route speaks Cursor's own agent protocol (`agent.v1.AgentService/Run`
|
|
5
|
+
* over HTTP/2) through the omp build artifact in `lib/omp/cursor.mjs`. The
|
|
6
|
+
* transport is injected rather than imported so this module stays free of the
|
|
7
|
+
* 14 MB build artifact and tests can replay recorded event scripts. The plugin
|
|
8
|
+
* wires the bundled `streamCursor` at registration and the credential seam
|
|
9
|
+
* provides {@link OmpCursorAdapterConfig.access}, which refreshes an expiring
|
|
10
|
+
* grant under the store's lock before it answers.
|
|
11
|
+
*
|
|
12
|
+
* The catalog is the generated `src/catalog/cursor.ts`, so `listModels` and
|
|
13
|
+
* `resolveModel` answer without a network call and carry the transport flags the
|
|
14
|
+
* projection needs (effort routing, max mode, glyph tokenization).
|
|
15
|
+
*
|
|
16
|
+
* @module dsh-llm-omp-transports/adapter
|
|
17
|
+
*/
|
|
18
|
+
import { LlmAdapter, LlmError, ReasoningEffortId, assertUsableApiKey } from '@deepseek-ai/dsh-llm';
|
|
19
|
+
import { CURSOR_MODELS } from './catalog/cursor.js';
|
|
20
|
+
import { CURSOR_CREDENTIAL_KEY } from './cursor/credentials.js';
|
|
21
|
+
import { abortedFinish, projectEvents, projectRequest } from './projection.js';
|
|
22
|
+
/** The provider route this adapter owns. */
|
|
23
|
+
export const CURSOR_ROUTE = 'cursor';
|
|
24
|
+
/** Machine code for a model id the generated catalog does not contain. */
|
|
25
|
+
export const UNKNOWN_MODEL = 'UNKNOWN_MODEL';
|
|
26
|
+
/** Machine code for a provider route this adapter does not serve. */
|
|
27
|
+
export const UNKNOWN_PROVIDER = 'UNKNOWN_PROVIDER';
|
|
28
|
+
/**
|
|
29
|
+
* Input modalities every advertised row carries.
|
|
30
|
+
*
|
|
31
|
+
* shortcut: the projection carries text only and refuses every non-text block
|
|
32
|
+
* with `CONTENT_UNSUPPORTED`, so advertising the catalog row's `input` verbatim
|
|
33
|
+
* (100 of 123 rows say `image`) would promise a turn this route fails after
|
|
34
|
+
* DSH's own image→text fallback is skipped. Task 2/3 add image forwarding; that
|
|
35
|
+
* is when `row.input` becomes advertisable again.
|
|
36
|
+
*/
|
|
37
|
+
const INPUT_MODALITIES = ['text'];
|
|
38
|
+
/** Display names for the catalog's reasoning efforts. */
|
|
39
|
+
const EFFORT_NAMES = {
|
|
40
|
+
minimal: 'Minimal',
|
|
41
|
+
low: 'Low',
|
|
42
|
+
medium: 'Medium',
|
|
43
|
+
high: 'High',
|
|
44
|
+
xhigh: 'Extra high',
|
|
45
|
+
max: 'Max',
|
|
46
|
+
};
|
|
47
|
+
/** The generated catalog, indexed for exact-model resolution. */
|
|
48
|
+
const MODELS_BY_ID = new Map(CURSOR_MODELS.map(row => [row.id, row]));
|
|
49
|
+
/** The DSH llm adapter for every route this plugin's omp transport serves. */
|
|
50
|
+
export class OmpCursorAdapter extends LlmAdapter {
|
|
51
|
+
config;
|
|
52
|
+
constructor(config) {
|
|
53
|
+
super();
|
|
54
|
+
this.config = config;
|
|
55
|
+
}
|
|
56
|
+
/**
|
|
57
|
+
* Describe the route.
|
|
58
|
+
*
|
|
59
|
+
* @remarks
|
|
60
|
+
* Cursor's agent protocol takes no client-side output cap, sampling
|
|
61
|
+
* temperature, stop sequence or auxiliary-call purpose: the wire carries no
|
|
62
|
+
* field for any of them, so the projection ignores those `GenerateOptions`
|
|
63
|
+
* values instead of forwarding them. Cursor applies the catalog `maxTokens`
|
|
64
|
+
* limit server-side.
|
|
65
|
+
*/
|
|
66
|
+
providerInfo(provider) {
|
|
67
|
+
return { id: provider, name: 'Cursor' };
|
|
68
|
+
}
|
|
69
|
+
async listModels(provider) {
|
|
70
|
+
assertRoute(provider);
|
|
71
|
+
return CURSOR_MODELS.map(row => ({
|
|
72
|
+
provider,
|
|
73
|
+
id: row.id,
|
|
74
|
+
name: row.name,
|
|
75
|
+
inputModalities: [...INPUT_MODALITIES],
|
|
76
|
+
}));
|
|
77
|
+
}
|
|
78
|
+
async resolveModel(provider, model) {
|
|
79
|
+
assertRoute(provider);
|
|
80
|
+
return modelInfo(provider, rowFor(model));
|
|
81
|
+
}
|
|
82
|
+
stream(options) {
|
|
83
|
+
return this.call(options);
|
|
84
|
+
}
|
|
85
|
+
async *call(options) {
|
|
86
|
+
// Read the live signal each time: it can abort while the credential is read.
|
|
87
|
+
const aborted = () => options.signal?.aborted === true;
|
|
88
|
+
// An already-cancelled turn must not pay a credential read (nor, once the
|
|
89
|
+
// resolver refreshes, a CAS write) or open a stream.
|
|
90
|
+
if (aborted()) {
|
|
91
|
+
yield abortedFinish();
|
|
92
|
+
return;
|
|
93
|
+
}
|
|
94
|
+
const row = rowFor(options.model);
|
|
95
|
+
// Validate and project before touching the credential: a refused request
|
|
96
|
+
// must not pay a credential read (nor, once the resolver refreshes, a CAS
|
|
97
|
+
// write). Only a request that can be served resolves `access` and carries
|
|
98
|
+
// its token into the transport options.
|
|
99
|
+
const request = projectRequest(row, options);
|
|
100
|
+
let credential;
|
|
101
|
+
try {
|
|
102
|
+
credential = await this.config.access(options.signal);
|
|
103
|
+
}
|
|
104
|
+
catch (error) {
|
|
105
|
+
// The resolver rejects when the caller aborts (a refresh is abandoned,
|
|
106
|
+
// not failed), so that rejection is the turn's cancellation. A genuine
|
|
107
|
+
// credential failure has no aborted signal and still propagates.
|
|
108
|
+
if (!aborted())
|
|
109
|
+
throw error;
|
|
110
|
+
yield abortedFinish();
|
|
111
|
+
return;
|
|
112
|
+
}
|
|
113
|
+
const accessKey = assertUsableApiKey(credential, 'llm-omp-transports', CURSOR_CREDENTIAL_KEY);
|
|
114
|
+
if (aborted()) {
|
|
115
|
+
yield abortedFinish();
|
|
116
|
+
return;
|
|
117
|
+
}
|
|
118
|
+
const transportOptions = { ...request.options, apiKey: accessKey };
|
|
119
|
+
yield* projectEvents(this.config.transport(request.model, request.context, transportOptions), options.signal);
|
|
120
|
+
}
|
|
121
|
+
}
|
|
122
|
+
/** Resolve one catalog row, refusing ids the pinned catalog does not serve. */
|
|
123
|
+
function rowFor(model) {
|
|
124
|
+
const row = MODELS_BY_ID.get(model);
|
|
125
|
+
if (row === undefined) {
|
|
126
|
+
throw new LlmError(`llm-omp-transports: the cursor route has no model "${model}"`, UNKNOWN_MODEL);
|
|
127
|
+
}
|
|
128
|
+
return row;
|
|
129
|
+
}
|
|
130
|
+
/** Refuse routes this adapter does not own instead of describing another provider's models. */
|
|
131
|
+
function assertRoute(provider) {
|
|
132
|
+
if (provider !== CURSOR_ROUTE) {
|
|
133
|
+
throw new LlmError(`llm-omp-transports: the cursor adapter does not serve provider "${provider}"`, UNKNOWN_PROVIDER);
|
|
134
|
+
}
|
|
135
|
+
}
|
|
136
|
+
/** Build the seam's exact-model metadata from one catalog row. */
|
|
137
|
+
function modelInfo(provider, row) {
|
|
138
|
+
const efforts = row.thinking?.efforts ?? [];
|
|
139
|
+
return {
|
|
140
|
+
provider,
|
|
141
|
+
id: row.id,
|
|
142
|
+
name: row.name,
|
|
143
|
+
inputModalities: [...INPUT_MODALITIES],
|
|
144
|
+
context: { contextWindow: row.contextWindow },
|
|
145
|
+
// No `defaultMaxTokens`. The seam materializes that number into `maxTokens`
|
|
146
|
+
// on every request that omits one, and Cursor's wire has no per-request
|
|
147
|
+
// output-cap field: the projection ignores `maxTokens` rather than
|
|
148
|
+
// forwarding it, so advertising a default would only promise a cap nothing
|
|
149
|
+
// enforces. Cursor applies the catalog cap server-side, from the `maxTokens`
|
|
150
|
+
// the model object already carries.
|
|
151
|
+
// Every effort list is advertised exactly as the catalog declares it. On a
|
|
152
|
+
// row with no `effortRouting` entry each advertised effort resolves to the
|
|
153
|
+
// same wire id — the row's own — so those selections are wire-level no-ops,
|
|
154
|
+
// exactly as in omp.
|
|
155
|
+
...(efforts.length > 0
|
|
156
|
+
? {
|
|
157
|
+
reasoning: {
|
|
158
|
+
efforts: efforts.map(effort => ({
|
|
159
|
+
id: ReasoningEffortId(effort),
|
|
160
|
+
name: EFFORT_NAMES[effort] ?? effort,
|
|
161
|
+
})),
|
|
162
|
+
},
|
|
163
|
+
}
|
|
164
|
+
: {}),
|
|
165
|
+
};
|
|
166
|
+
}
|
|
167
|
+
//# sourceMappingURL=adapter.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"adapter.js","sourceRoot":"","sources":["../src/adapter.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Generated Cursor model table — do not edit by hand.
|
|
3
|
+
*
|
|
4
|
+
* Source: `@oh-my-pi/pi-catalog@18.12.3` `src/models.json` key `cursor`
|
|
5
|
+
* (123 rows, sha256:39fb09654ee3812043bc062e426d8e7aa13cd273435fa7b8a203a76246c8735c). Regenerate with `pnpm -C packages/llm-omp run generate:catalog`.
|
|
6
|
+
*
|
|
7
|
+
* The drift gate in `tests/build.test.ts` pins the same package version and
|
|
8
|
+
* source hash, so an omp bump fails there before this table can describe the
|
|
9
|
+
* wrong models.
|
|
10
|
+
*
|
|
11
|
+
* Rows that advertise efforts without routing them are carried unchanged, and
|
|
12
|
+
* on each of them every advertised effort resolves to the same wire id (the
|
|
13
|
+
* row's own, `requestModelId ?? id`): selecting one is a wire-level no-op,
|
|
14
|
+
* exactly as in omp. No row's effort list is filtered.
|
|
15
|
+
*
|
|
16
|
+
* @module dsh-llm-omp-transports/catalog/cursor
|
|
17
|
+
*/
|
|
18
|
+
import type { CursorModelRow } from '../omp.js';
|
|
19
|
+
/** Provenance of {@link CURSOR_MODELS}. */
|
|
20
|
+
export declare const CURSOR_CATALOG_SOURCE: {
|
|
21
|
+
readonly package: "@oh-my-pi/pi-catalog";
|
|
22
|
+
readonly version: "18.12.3";
|
|
23
|
+
readonly file: "src/models.json";
|
|
24
|
+
readonly key: "cursor";
|
|
25
|
+
readonly sourceHash: "sha256:39fb09654ee3812043bc062e426d8e7aa13cd273435fa7b8a203a76246c8735c";
|
|
26
|
+
readonly rowCount: 123;
|
|
27
|
+
};
|
|
28
|
+
/** Every Cursor model the pinned catalog serves, sorted by id. */
|
|
29
|
+
export declare const CURSOR_MODELS: readonly CursorModelRow[];
|