@oharness/engine 0.1.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.
- package/dist/agent/agent.d.ts +196 -0
- package/dist/agent/agent.js +758 -0
- package/dist/agent/agent.js.map +1 -0
- package/dist/agent/compaction.d.ts +68 -0
- package/dist/agent/compaction.js +179 -0
- package/dist/agent/compaction.js.map +1 -0
- package/dist/agent/hooks.d.ts +77 -0
- package/dist/agent/hooks.js +152 -0
- package/dist/agent/hooks.js.map +1 -0
- package/dist/agent/memory.d.ts +45 -0
- package/dist/agent/memory.js +147 -0
- package/dist/agent/memory.js.map +1 -0
- package/dist/agent/overflow.d.ts +35 -0
- package/dist/agent/overflow.js +69 -0
- package/dist/agent/overflow.js.map +1 -0
- package/dist/agent/permissions.d.ts +181 -0
- package/dist/agent/permissions.js +289 -0
- package/dist/agent/permissions.js.map +1 -0
- package/dist/agent/prompt.d.ts +25 -0
- package/dist/agent/prompt.js +63 -0
- package/dist/agent/prompt.js.map +1 -0
- package/dist/agent/session.d.ts +108 -0
- package/dist/agent/session.js +231 -0
- package/dist/agent/session.js.map +1 -0
- package/dist/agent/settings.d.ts +37 -0
- package/dist/agent/settings.js +113 -0
- package/dist/agent/settings.js.map +1 -0
- package/dist/agent/skills.d.ts +58 -0
- package/dist/agent/skills.js +225 -0
- package/dist/agent/skills.js.map +1 -0
- package/dist/agent/store.d.ts +308 -0
- package/dist/agent/store.js +596 -0
- package/dist/agent/store.js.map +1 -0
- package/dist/agent/subagent.d.ts +44 -0
- package/dist/agent/subagent.js +138 -0
- package/dist/agent/subagent.js.map +1 -0
- package/dist/agent/titles.d.ts +8 -0
- package/dist/agent/titles.js +23 -0
- package/dist/agent/titles.js.map +1 -0
- package/dist/agent/workspace.d.ts +60 -0
- package/dist/agent/workspace.js +156 -0
- package/dist/agent/workspace.js.map +1 -0
- package/dist/artifacts/publish.d.ts +94 -0
- package/dist/artifacts/publish.js +104 -0
- package/dist/artifacts/publish.js.map +1 -0
- package/dist/artifacts/store.d.ts +324 -0
- package/dist/artifacts/store.js +500 -0
- package/dist/artifacts/store.js.map +1 -0
- package/dist/auth/index.d.ts +13 -0
- package/dist/auth/index.js +10 -0
- package/dist/auth/index.js.map +1 -0
- package/dist/auth/manager.d.ts +83 -0
- package/dist/auth/manager.js +266 -0
- package/dist/auth/manager.js.map +1 -0
- package/dist/auth/oauth.d.ts +83 -0
- package/dist/auth/oauth.js +327 -0
- package/dist/auth/oauth.js.map +1 -0
- package/dist/auth/providers/account.d.ts +59 -0
- package/dist/auth/providers/account.js +282 -0
- package/dist/auth/providers/account.js.map +1 -0
- package/dist/auth/providers/anthropic.d.ts +24 -0
- package/dist/auth/providers/anthropic.js +209 -0
- package/dist/auth/providers/anthropic.js.map +1 -0
- package/dist/auth/providers/generic.d.ts +57 -0
- package/dist/auth/providers/generic.js +155 -0
- package/dist/auth/providers/generic.js.map +1 -0
- package/dist/auth/providers/official.d.ts +3 -0
- package/dist/auth/providers/official.js +90 -0
- package/dist/auth/providers/official.js.map +1 -0
- package/dist/auth/providers/ottoport.d.ts +3 -0
- package/dist/auth/providers/ottoport.js +60 -0
- package/dist/auth/providers/ottoport.js.map +1 -0
- package/dist/auth/store.d.ts +22 -0
- package/dist/auth/store.js +138 -0
- package/dist/auth/store.js.map +1 -0
- package/dist/auth/types.d.ts +167 -0
- package/dist/auth/types.js +16 -0
- package/dist/auth/types.js.map +1 -0
- package/dist/config.d.ts +197 -0
- package/dist/config.js +195 -0
- package/dist/config.js.map +1 -0
- package/dist/core/errors.d.ts +46 -0
- package/dist/core/errors.js +83 -0
- package/dist/core/errors.js.map +1 -0
- package/dist/core/tokens.d.ts +12 -0
- package/dist/core/tokens.js +56 -0
- package/dist/core/tokens.js.map +1 -0
- package/dist/core/types.d.ts +91 -0
- package/dist/core/types.js +49 -0
- package/dist/core/types.js.map +1 -0
- package/dist/harness.d.ts +302 -0
- package/dist/harness.js +695 -0
- package/dist/harness.js.map +1 -0
- package/dist/index.d.ts +32 -0
- package/dist/index.js +21 -0
- package/dist/index.js.map +1 -0
- package/dist/mcp/client.d.ts +55 -0
- package/dist/mcp/client.js +199 -0
- package/dist/mcp/client.js.map +1 -0
- package/dist/mcp/index.d.ts +13 -0
- package/dist/mcp/index.js +8 -0
- package/dist/mcp/index.js.map +1 -0
- package/dist/mcp/manager.d.ts +77 -0
- package/dist/mcp/manager.js +325 -0
- package/dist/mcp/manager.js.map +1 -0
- package/dist/mcp/oauth.d.ts +63 -0
- package/dist/mcp/oauth.js +302 -0
- package/dist/mcp/oauth.js.map +1 -0
- package/dist/mcp/protocol.d.ts +130 -0
- package/dist/mcp/protocol.js +14 -0
- package/dist/mcp/protocol.js.map +1 -0
- package/dist/mcp/registry.d.ts +52 -0
- package/dist/mcp/registry.js +100 -0
- package/dist/mcp/registry.js.map +1 -0
- package/dist/mcp/registry.json +293 -0
- package/dist/mcp/secrets.d.ts +20 -0
- package/dist/mcp/secrets.js +75 -0
- package/dist/mcp/secrets.js.map +1 -0
- package/dist/mcp/transport.d.ts +51 -0
- package/dist/mcp/transport.js +158 -0
- package/dist/mcp/transport.js.map +1 -0
- package/dist/paths.d.ts +37 -0
- package/dist/paths.js +63 -0
- package/dist/paths.js.map +1 -0
- package/dist/plugins.d.ts +55 -0
- package/dist/plugins.js +201 -0
- package/dist/plugins.js.map +1 -0
- package/dist/providers/builtin.d.ts +23 -0
- package/dist/providers/builtin.js +141 -0
- package/dist/providers/builtin.js.map +1 -0
- package/dist/providers/catalog.d.ts +129 -0
- package/dist/providers/catalog.js +254 -0
- package/dist/providers/catalog.js.map +1 -0
- package/dist/providers/catalog.json +472 -0
- package/dist/providers/discovery.d.ts +16 -0
- package/dist/providers/discovery.js +161 -0
- package/dist/providers/discovery.js.map +1 -0
- package/dist/providers/http.d.ts +24 -0
- package/dist/providers/http.js +139 -0
- package/dist/providers/http.js.map +1 -0
- package/dist/providers/index.d.ts +10 -0
- package/dist/providers/index.js +8 -0
- package/dist/providers/index.js.map +1 -0
- package/dist/providers/piai.d.ts +124 -0
- package/dist/providers/piai.js +551 -0
- package/dist/providers/piai.js.map +1 -0
- package/dist/providers/registry.d.ts +65 -0
- package/dist/providers/registry.js +195 -0
- package/dist/providers/registry.js.map +1 -0
- package/dist/providers/resilient.d.ts +46 -0
- package/dist/providers/resilient.js +117 -0
- package/dist/providers/resilient.js.map +1 -0
- package/dist/providers/types.d.ts +182 -0
- package/dist/providers/types.js +50 -0
- package/dist/providers/types.js.map +1 -0
- package/dist/schedule/cron.d.ts +35 -0
- package/dist/schedule/cron.js +125 -0
- package/dist/schedule/cron.js.map +1 -0
- package/dist/schedule/scheduler.d.ts +87 -0
- package/dist/schedule/scheduler.js +237 -0
- package/dist/schedule/scheduler.js.map +1 -0
- package/dist/storage/kv.d.ts +56 -0
- package/dist/storage/kv.js +173 -0
- package/dist/storage/kv.js.map +1 -0
- package/dist/storage/migrate.d.ts +11 -0
- package/dist/storage/migrate.js +93 -0
- package/dist/storage/migrate.js.map +1 -0
- package/dist/storage/project.d.ts +9 -0
- package/dist/storage/project.js +57 -0
- package/dist/storage/project.js.map +1 -0
- package/dist/storage/records.d.ts +32 -0
- package/dist/storage/records.js +48 -0
- package/dist/storage/records.js.map +1 -0
- package/dist/sync/client.d.ts +79 -0
- package/dist/sync/client.js +118 -0
- package/dist/sync/client.js.map +1 -0
- package/dist/sync/mirror.d.ts +85 -0
- package/dist/sync/mirror.js +389 -0
- package/dist/sync/mirror.js.map +1 -0
- package/dist/sync/protocol.d.ts +67 -0
- package/dist/sync/protocol.js +16 -0
- package/dist/sync/protocol.js.map +1 -0
- package/dist/sync/settings.d.ts +56 -0
- package/dist/sync/settings.js +60 -0
- package/dist/sync/settings.js.map +1 -0
- package/dist/tools/builtin/artifact.d.ts +16 -0
- package/dist/tools/builtin/artifact.js +134 -0
- package/dist/tools/builtin/artifact.js.map +1 -0
- package/dist/tools/builtin/bash.d.ts +3 -0
- package/dist/tools/builtin/bash.js +142 -0
- package/dist/tools/builtin/bash.js.map +1 -0
- package/dist/tools/builtin/fs.d.ts +19 -0
- package/dist/tools/builtin/fs.js +280 -0
- package/dist/tools/builtin/fs.js.map +1 -0
- package/dist/tools/builtin/index.d.ts +22 -0
- package/dist/tools/builtin/index.js +42 -0
- package/dist/tools/builtin/index.js.map +1 -0
- package/dist/tools/builtin/mcp-resource.d.ts +3 -0
- package/dist/tools/builtin/mcp-resource.js +220 -0
- package/dist/tools/builtin/mcp-resource.js.map +1 -0
- package/dist/tools/builtin/memory.d.ts +10 -0
- package/dist/tools/builtin/memory.js +76 -0
- package/dist/tools/builtin/memory.js.map +1 -0
- package/dist/tools/builtin/recall.d.ts +13 -0
- package/dist/tools/builtin/recall.js +163 -0
- package/dist/tools/builtin/recall.js.map +1 -0
- package/dist/tools/builtin/search.d.ts +3 -0
- package/dist/tools/builtin/search.js +240 -0
- package/dist/tools/builtin/search.js.map +1 -0
- package/dist/tools/builtin/skill.d.ts +10 -0
- package/dist/tools/builtin/skill.js +46 -0
- package/dist/tools/builtin/skill.js.map +1 -0
- package/dist/tools/builtin/task.d.ts +9 -0
- package/dist/tools/builtin/task.js +68 -0
- package/dist/tools/builtin/task.js.map +1 -0
- package/dist/tools/builtin/todo.d.ts +20 -0
- package/dist/tools/builtin/todo.js +63 -0
- package/dist/tools/builtin/todo.js.map +1 -0
- package/dist/tools/define.d.ts +19 -0
- package/dist/tools/define.js +39 -0
- package/dist/tools/define.js.map +1 -0
- package/dist/tools/index.d.ts +7 -0
- package/dist/tools/index.js +5 -0
- package/dist/tools/index.js.map +1 -0
- package/dist/tools/registry.d.ts +39 -0
- package/dist/tools/registry.js +101 -0
- package/dist/tools/registry.js.map +1 -0
- package/dist/tools/types.d.ts +112 -0
- package/dist/tools/types.js +22 -0
- package/dist/tools/types.js.map +1 -0
- package/dist/util/id.d.ts +9 -0
- package/dist/util/id.js +19 -0
- package/dist/util/id.js.map +1 -0
- package/dist/util/json.d.ts +25 -0
- package/dist/util/json.js +100 -0
- package/dist/util/json.js.map +1 -0
- package/dist/util/jwt.d.ts +74 -0
- package/dist/util/jwt.js +177 -0
- package/dist/util/jwt.js.map +1 -0
- package/dist/util/logger.d.ts +13 -0
- package/dist/util/logger.js +59 -0
- package/dist/util/logger.js.map +1 -0
- package/dist/util/queue.d.ts +26 -0
- package/dist/util/queue.js +106 -0
- package/dist/util/queue.js.map +1 -0
- package/dist/util/schema.d.ts +17 -0
- package/dist/util/schema.js +98 -0
- package/dist/util/schema.js.map +1 -0
- package/dist/util/shell.d.ts +20 -0
- package/dist/util/shell.js +24 -0
- package/dist/util/shell.js.map +1 -0
- package/official.json +4 -0
- package/package.json +38 -0
- package/skills/artifact-authoring/SKILL.md +81 -0
- package/skills/canvas/SKILL.md +85 -0
- package/skills/skill-authoring/SKILL.md +85 -0
|
@@ -0,0 +1,551 @@
|
|
|
1
|
+
import { anthropicMessagesApi } from "@earendil-works/pi-ai/api/anthropic-messages.lazy";
|
|
2
|
+
import { bedrockConverseStreamApi } from "@earendil-works/pi-ai/api/bedrock-converse-stream.lazy";
|
|
3
|
+
import { googleGenerativeAIApi } from "@earendil-works/pi-ai/api/google-generative-ai.lazy";
|
|
4
|
+
import { googleVertexApi } from "@earendil-works/pi-ai/api/google-vertex.lazy";
|
|
5
|
+
import { openAICompletionsApi } from "@earendil-works/pi-ai/api/openai-completions.lazy";
|
|
6
|
+
import { openAIResponsesApi } from "@earendil-works/pi-ai/api/openai-responses.lazy";
|
|
7
|
+
import { ProviderError } from "../core/errors.js";
|
|
8
|
+
import { uuid } from "../util/id.js";
|
|
9
|
+
import { emptyUsage } from "../core/types.js";
|
|
10
|
+
import { discoverModels } from "./discovery.js";
|
|
11
|
+
import { applyAuthHeaders, resolveEffort } from "./types.js";
|
|
12
|
+
/**
|
|
13
|
+
* Lazily-loaded implementations. The `.lazy` wrappers defer loading the vendor
|
|
14
|
+
* SDK until the first request to that protocol, so a session that only talks to
|
|
15
|
+
* Anthropic never loads the AWS or Google clients.
|
|
16
|
+
*/
|
|
17
|
+
const APIS = {
|
|
18
|
+
"anthropic-messages": anthropicMessagesApi,
|
|
19
|
+
"openai-completions": openAICompletionsApi,
|
|
20
|
+
"openai-responses": openAIResponsesApi,
|
|
21
|
+
"google-generative-ai": googleGenerativeAIApi,
|
|
22
|
+
"google-vertex": googleVertexApi,
|
|
23
|
+
"bedrock-converse-stream": bedrockConverseStreamApi,
|
|
24
|
+
};
|
|
25
|
+
/**
|
|
26
|
+
* The pi-ai API implementation behind each catalog protocol.
|
|
27
|
+
*
|
|
28
|
+
* The catalog's names are the harness's own and predate pi-ai; keeping the
|
|
29
|
+
* mapping explicit means a rename upstream is a one-line change here rather
|
|
30
|
+
* than a migration of every user's catalog.json. It lives beside `PiApi`
|
|
31
|
+
* because both the registry (which builds providers) and the builtin seed
|
|
32
|
+
* (which decides whether a pi-ai model can even be driven over a catalog
|
|
33
|
+
* entry's protocol) have to agree on it.
|
|
34
|
+
*/
|
|
35
|
+
export const PI_APIS = {
|
|
36
|
+
"anthropic-messages": "anthropic-messages",
|
|
37
|
+
"openai-chat": "openai-completions",
|
|
38
|
+
gemini: "google-generative-ai",
|
|
39
|
+
"openai-responses": "openai-responses",
|
|
40
|
+
bedrock: "bedrock-converse-stream",
|
|
41
|
+
vertex: "google-vertex",
|
|
42
|
+
};
|
|
43
|
+
const streamsCache = new Map();
|
|
44
|
+
function streamsFor(api) {
|
|
45
|
+
let streams = streamsCache.get(api);
|
|
46
|
+
if (!streams) {
|
|
47
|
+
streams = APIS[api]();
|
|
48
|
+
streamsCache.set(api, streams);
|
|
49
|
+
}
|
|
50
|
+
return streams;
|
|
51
|
+
}
|
|
52
|
+
export class PiAiProvider {
|
|
53
|
+
id;
|
|
54
|
+
name;
|
|
55
|
+
opts;
|
|
56
|
+
/**
|
|
57
|
+
* Only defined when the endpoint publishes a `/models` listing — callers
|
|
58
|
+
* test for its presence, so defining it unconditionally would make every
|
|
59
|
+
* provider claim it can enumerate models.
|
|
60
|
+
*/
|
|
61
|
+
listModels;
|
|
62
|
+
constructor(opts) {
|
|
63
|
+
this.opts = opts;
|
|
64
|
+
this.id = opts.id;
|
|
65
|
+
this.name = opts.name ?? opts.id;
|
|
66
|
+
// `/models` is the OpenAI dialect's convention. Anthropic and Google
|
|
67
|
+
// publish no equivalent, so those providers must not claim they can
|
|
68
|
+
// enumerate — `refreshModels` tests for the method, not for a result.
|
|
69
|
+
if (opts.api === "openai-completions" || opts.api === "openai-responses") {
|
|
70
|
+
this.listModels = () => discoverModels({
|
|
71
|
+
providerId: this.id,
|
|
72
|
+
baseUrl: this.baseUrl(),
|
|
73
|
+
apiKey: this.apiKey(),
|
|
74
|
+
headers: this.opts.headers,
|
|
75
|
+
auth: this.opts.auth,
|
|
76
|
+
format: this.opts.discoveryFormat,
|
|
77
|
+
});
|
|
78
|
+
}
|
|
79
|
+
}
|
|
80
|
+
isConfigured() {
|
|
81
|
+
if (this.opts.requiresKey === false)
|
|
82
|
+
return true;
|
|
83
|
+
return Boolean(this.apiKey());
|
|
84
|
+
}
|
|
85
|
+
apiKey() {
|
|
86
|
+
return (this.opts.apiKey ?? (this.opts.apiKeyEnv ? process.env[this.opts.apiKeyEnv] : undefined));
|
|
87
|
+
}
|
|
88
|
+
baseUrl() {
|
|
89
|
+
return (this.opts.baseUrl ?? "").replace(/\/+$/, "");
|
|
90
|
+
}
|
|
91
|
+
async *stream(request) {
|
|
92
|
+
const resolved = await this.opts.auth?.({ providerId: this.id, url: this.baseUrl() });
|
|
93
|
+
const apiKey = credentialFrom(resolved) ?? this.apiKey();
|
|
94
|
+
if (this.opts.requiresKey !== false && !apiKey && !resolved) {
|
|
95
|
+
throw new ProviderError(this.id, `no credentials (set ${this.opts.apiKeyEnv ?? "the provider's API key env var"}, or run \`oharness auth login ${this.id}\`)`, { retryable: false });
|
|
96
|
+
}
|
|
97
|
+
const model = this.toPiModel(request.model, resolved);
|
|
98
|
+
const streams = streamsFor(this.opts.api);
|
|
99
|
+
const reasoning = thinkingLevel(request);
|
|
100
|
+
const sampling = this.samplingParams(request);
|
|
101
|
+
const options = {
|
|
102
|
+
// Local servers need *something* here: the vendor SDKs refuse to
|
|
103
|
+
// construct without a key even when the endpoint ignores it.
|
|
104
|
+
apiKey: apiKey ?? "unused",
|
|
105
|
+
headers: this.requestHeaders(resolved),
|
|
106
|
+
maxTokens: this.maxTokensFor(request),
|
|
107
|
+
cacheRetention: request.cache ? "short" : "none",
|
|
108
|
+
...(request.signal ? { signal: request.signal } : {}),
|
|
109
|
+
...(request.model.supportsSampling && request.temperature !== undefined
|
|
110
|
+
? { temperature: request.temperature }
|
|
111
|
+
: {}),
|
|
112
|
+
...(reasoning ? { reasoning } : {}),
|
|
113
|
+
...(sampling ? { samplingParams: sampling } : {}),
|
|
114
|
+
...(this.opts.timeoutMs ? { timeoutMs: this.opts.timeoutMs } : {}),
|
|
115
|
+
...(this.opts.maxRetries !== undefined ? { maxRetries: this.opts.maxRetries } : {}),
|
|
116
|
+
};
|
|
117
|
+
const context = toPiContext(request, {
|
|
118
|
+
providerId: this.id,
|
|
119
|
+
thinkingOn: options.reasoning !== undefined,
|
|
120
|
+
});
|
|
121
|
+
yield* mapEvents(streams.streamSimple(model, context, options), this.id, request.model.model);
|
|
122
|
+
}
|
|
123
|
+
/**
|
|
124
|
+
* Sampling knobs pi-ai does not model. They are merged into the request body
|
|
125
|
+
* verbatim by the OpenAI-compatible adapters only, so anything sent here is
|
|
126
|
+
* silently dropped by the Anthropic, Google and Bedrock protocols.
|
|
127
|
+
*/
|
|
128
|
+
samplingParams(request) {
|
|
129
|
+
const openAiFamily = this.opts.api === "openai-completions" || this.opts.api === "openai-responses";
|
|
130
|
+
if (!openAiFamily)
|
|
131
|
+
return undefined;
|
|
132
|
+
const params = {
|
|
133
|
+
...(request.model.supportsSampling && request.topP !== undefined
|
|
134
|
+
? { top_p: request.topP }
|
|
135
|
+
: {}),
|
|
136
|
+
...(request.stopSequences?.length ? { stop: request.stopSequences } : {}),
|
|
137
|
+
...request.extraBody,
|
|
138
|
+
};
|
|
139
|
+
return Object.keys(params).length ? params : undefined;
|
|
140
|
+
}
|
|
141
|
+
/**
|
|
142
|
+
* How many tokens to ask for, under whatever ceiling the endpoint imposes.
|
|
143
|
+
*
|
|
144
|
+
* The model's own limit is the usual answer. A gateway that caps output
|
|
145
|
+
* below it is a separate fact — the models it serves still advertise their
|
|
146
|
+
* real maximum, and a request over the gateway's line is refused rather than
|
|
147
|
+
* truncated, so the clamp has to happen here on the way out.
|
|
148
|
+
*/
|
|
149
|
+
maxTokensFor(request) {
|
|
150
|
+
const asked = request.maxOutputTokens ?? request.model.maxOutputTokens;
|
|
151
|
+
return this.opts.maxOutputTokens ? Math.min(asked, this.opts.maxOutputTokens) : asked;
|
|
152
|
+
}
|
|
153
|
+
/**
|
|
154
|
+
* Provider headers plus whatever the resolver produced. A `null` value
|
|
155
|
+
* suppresses a header the SDK would otherwise set: bearer-token auth must
|
|
156
|
+
* remove the `x-api-key` the Anthropic client adds from `apiKey`, or the API
|
|
157
|
+
* sees two conflicting credentials and rejects the request.
|
|
158
|
+
*
|
|
159
|
+
* Called once per `stream()`, which is what makes the idempotency key below
|
|
160
|
+
* correct: pi-ai's own retries reuse this object and so resend the same key,
|
|
161
|
+
* which is how a gateway is told "this is the call that already reserved,
|
|
162
|
+
* not a new one" — while a retry the harness decides on comes back through
|
|
163
|
+
* `stream()` and gets a fresh key, because by then the first attempt may
|
|
164
|
+
* have been billed.
|
|
165
|
+
*/
|
|
166
|
+
requestHeaders(resolved) {
|
|
167
|
+
const headers = { ...this.opts.headers };
|
|
168
|
+
if (this.opts.idempotencyKey)
|
|
169
|
+
headers["idempotency-key"] = uuid();
|
|
170
|
+
for (const name of resolved?.removeHeaders ?? []) {
|
|
171
|
+
headers[name] = null;
|
|
172
|
+
headers[name.toLowerCase()] = null;
|
|
173
|
+
}
|
|
174
|
+
for (const [name, value] of Object.entries(resolved?.headers ?? {})) {
|
|
175
|
+
headers[name] = value;
|
|
176
|
+
}
|
|
177
|
+
return headers;
|
|
178
|
+
}
|
|
179
|
+
/** Translate a harness model spec into the shape pi-ai dispatches on. */
|
|
180
|
+
toPiModel(spec, resolved) {
|
|
181
|
+
const reasoning = spec.thinkingMode !== "none";
|
|
182
|
+
return {
|
|
183
|
+
id: spec.model,
|
|
184
|
+
name: spec.displayName ?? spec.model,
|
|
185
|
+
api: this.opts.api,
|
|
186
|
+
provider: this.id,
|
|
187
|
+
baseUrl: resolved?.baseUrl ?? this.baseUrl(),
|
|
188
|
+
reasoning,
|
|
189
|
+
...(reasoning ? { thinkingLevelMap: thinkingLevelMap(spec) } : {}),
|
|
190
|
+
// Declared image input where the harness cannot rule it out, not only
|
|
191
|
+
// where it was promised: pi-ai's OpenAI adapter drops the images in a
|
|
192
|
+
// tool result unless this says "image", and a discovered model whose
|
|
193
|
+
// endpoint published no capabilities at all would silently lose every
|
|
194
|
+
// screenshot `read` returned. Only a model documented as text-only is
|
|
195
|
+
// narrowed, where the refusal is a fact rather than a guess.
|
|
196
|
+
input: spec.supportsImages || spec.capabilitiesAssumed ? ["text", "image"] : ["text"],
|
|
197
|
+
cost: {
|
|
198
|
+
input: spec.costPer1MInput ?? 0,
|
|
199
|
+
output: spec.costPer1MOutput ?? 0,
|
|
200
|
+
cacheRead: spec.costPer1MCacheRead ?? 0,
|
|
201
|
+
cacheWrite: spec.costPer1MCacheWrite ?? 0,
|
|
202
|
+
},
|
|
203
|
+
contextWindow: spec.contextWindow,
|
|
204
|
+
maxTokens: spec.maxOutputTokens,
|
|
205
|
+
compat: this.compatFor(spec),
|
|
206
|
+
};
|
|
207
|
+
}
|
|
208
|
+
/**
|
|
209
|
+
* Per-protocol quirks the catalog knows about. pi-ai auto-detects these from
|
|
210
|
+
* the base URL for vendors it recognizes; everything here is the subset the
|
|
211
|
+
* catalog states outright, which must win over a guess made from a hostname.
|
|
212
|
+
*/
|
|
213
|
+
compatFor(spec) {
|
|
214
|
+
switch (this.opts.api) {
|
|
215
|
+
case "anthropic-messages":
|
|
216
|
+
return {
|
|
217
|
+
// A model that only accepts `{type:"adaptive"}` rejects a
|
|
218
|
+
// budget_tokens config outright — this is a 400, not a degradation.
|
|
219
|
+
...(spec.thinkingMode === "adaptive" ? { forceAdaptiveThinking: true } : {}),
|
|
220
|
+
...(spec.supportsSampling ? {} : { supportsTemperature: false }),
|
|
221
|
+
};
|
|
222
|
+
case "openai-completions": {
|
|
223
|
+
const local = this.opts.requiresKey === false;
|
|
224
|
+
return {
|
|
225
|
+
...(this.opts.includeUsage === false ? { supportsUsageInStreaming: false } : {}),
|
|
226
|
+
// Local servers (Ollama, vLLM, LM Studio) speak an older dialect:
|
|
227
|
+
// no `developer` role, no `reasoning_effort`.
|
|
228
|
+
...(local ? { supportsDeveloperRole: false, supportsReasoningEffort: false } : {}),
|
|
229
|
+
};
|
|
230
|
+
}
|
|
231
|
+
default:
|
|
232
|
+
return undefined;
|
|
233
|
+
}
|
|
234
|
+
}
|
|
235
|
+
}
|
|
236
|
+
// ---------------------------------------------------------------------------
|
|
237
|
+
// Request translation
|
|
238
|
+
// ---------------------------------------------------------------------------
|
|
239
|
+
/**
|
|
240
|
+
* The thinking tier to ask for, clamped to what the model accepts.
|
|
241
|
+
*
|
|
242
|
+
* pi-ai takes one unified level and each protocol renders it its own way
|
|
243
|
+
* (Anthropic budget or adaptive effort, OpenAI `reasoning_effort`, Gemini
|
|
244
|
+
* thinking config), so the harness no longer has to know which is which. What
|
|
245
|
+
* it does still have to know is when *not* to ask for a level: an absent level
|
|
246
|
+
* makes pi-ai disable thinking explicitly, and there are two models where that
|
|
247
|
+
* is a 400 rather than a preference.
|
|
248
|
+
*/
|
|
249
|
+
function thinkingLevel(request) {
|
|
250
|
+
const { thinking, model } = request;
|
|
251
|
+
if (model.thinkingMode === "none")
|
|
252
|
+
return undefined;
|
|
253
|
+
const level = resolveEffort(model, thinking?.effort) ?? "medium";
|
|
254
|
+
// Thinking cannot be turned off on these models, so honour the tier and
|
|
255
|
+
// ignore the switch rather than sending a disable the API rejects.
|
|
256
|
+
if (model.thinkingMode === "always-on")
|
|
257
|
+
return level;
|
|
258
|
+
if (thinking?.enabled)
|
|
259
|
+
return level;
|
|
260
|
+
// Some models reject a disable above a given tier. Asking for the tier is
|
|
261
|
+
// the only legal way to express "as configured" there.
|
|
262
|
+
const cap = model.maxEffortWithThinkingDisabled;
|
|
263
|
+
const above = cap && thinking?.effort && EFFORT_ORDER.indexOf(thinking.effort) > EFFORT_ORDER.indexOf(cap);
|
|
264
|
+
return above ? level : undefined;
|
|
265
|
+
}
|
|
266
|
+
const EFFORT_ORDER = ["low", "medium", "high", "xhigh", "max"];
|
|
267
|
+
/**
|
|
268
|
+
* Which tiers this model accepts. `null` marks a tier unsupported; `xhigh` and
|
|
269
|
+
* `max` are opt-in in pi-ai and need an explicit value to be reachable at all.
|
|
270
|
+
*/
|
|
271
|
+
function thinkingLevelMap(spec) {
|
|
272
|
+
const levels = ["minimal", "low", "medium", "high", "xhigh", "max"];
|
|
273
|
+
const map = {};
|
|
274
|
+
for (const level of levels) {
|
|
275
|
+
if (spec.effortLevels.length === 0)
|
|
276
|
+
continue;
|
|
277
|
+
map[level] = spec.effortLevels.includes(level) ? level : null;
|
|
278
|
+
}
|
|
279
|
+
return map;
|
|
280
|
+
}
|
|
281
|
+
function toPiContext(request, opts) {
|
|
282
|
+
return {
|
|
283
|
+
...(request.system ? { systemPrompt: request.system } : {}),
|
|
284
|
+
messages: request.messages.flatMap((message) => toPiMessages(message, opts)),
|
|
285
|
+
...(request.tools?.length ? { tools: request.tools.map(toPiTool) } : {}),
|
|
286
|
+
};
|
|
287
|
+
}
|
|
288
|
+
function toPiTool(tool) {
|
|
289
|
+
// pi-ai types parameters as a TypeBox schema, which is a plain JSON Schema
|
|
290
|
+
// object at runtime. The harness carries JSON Schema throughout, so this is
|
|
291
|
+
// a type assertion rather than a conversion.
|
|
292
|
+
return {
|
|
293
|
+
name: tool.name,
|
|
294
|
+
description: tool.description,
|
|
295
|
+
parameters: tool.inputSchema,
|
|
296
|
+
};
|
|
297
|
+
}
|
|
298
|
+
/**
|
|
299
|
+
* One harness message can become several pi-ai messages.
|
|
300
|
+
*
|
|
301
|
+
* The harness stores tool results as blocks inside the *user* message that
|
|
302
|
+
* carries them, because that is how the conversation reads. pi-ai models them
|
|
303
|
+
* as their own `toolResult` role, so they are split out here — in order, since
|
|
304
|
+
* every provider requires a tool result to directly follow the call it answers.
|
|
305
|
+
*/
|
|
306
|
+
export function toPiMessages(message, opts) {
|
|
307
|
+
const timestamp = message.meta?.timestamp ?? Date.now();
|
|
308
|
+
if (message.role === "assistant") {
|
|
309
|
+
const content = [];
|
|
310
|
+
for (const block of message.content) {
|
|
311
|
+
switch (block.type) {
|
|
312
|
+
case "text":
|
|
313
|
+
content.push({ type: "text", text: block.text });
|
|
314
|
+
break;
|
|
315
|
+
case "thinking":
|
|
316
|
+
// A thinking block is only replayable with the signature the same
|
|
317
|
+
// provider issued. After a model switch we drop it rather than send
|
|
318
|
+
// something the API will reject — pi-ai has no way to know the turn
|
|
319
|
+
// came from somewhere else.
|
|
320
|
+
if (!opts.thinkingOn || message.meta?.provider !== opts.providerId)
|
|
321
|
+
break;
|
|
322
|
+
content.push({
|
|
323
|
+
type: "thinking",
|
|
324
|
+
thinking: block.thinking,
|
|
325
|
+
...(block.signature ? { thinkingSignature: block.signature } : {}),
|
|
326
|
+
...(block.redacted ? { redacted: true } : {}),
|
|
327
|
+
});
|
|
328
|
+
break;
|
|
329
|
+
case "tool_call":
|
|
330
|
+
content.push({
|
|
331
|
+
type: "toolCall",
|
|
332
|
+
id: block.id,
|
|
333
|
+
name: block.name,
|
|
334
|
+
arguments: (block.input ?? {}),
|
|
335
|
+
});
|
|
336
|
+
break;
|
|
337
|
+
default:
|
|
338
|
+
break;
|
|
339
|
+
}
|
|
340
|
+
}
|
|
341
|
+
const assistant = {
|
|
342
|
+
role: "assistant",
|
|
343
|
+
content,
|
|
344
|
+
api: "openai-completions",
|
|
345
|
+
provider: String(message.meta?.provider ?? opts.providerId),
|
|
346
|
+
model: String(message.meta?.model ?? ""),
|
|
347
|
+
usage: toPiUsage(message.meta?.usage),
|
|
348
|
+
stopReason: "stop",
|
|
349
|
+
timestamp,
|
|
350
|
+
};
|
|
351
|
+
return [assistant];
|
|
352
|
+
}
|
|
353
|
+
const out = [];
|
|
354
|
+
const direct = [];
|
|
355
|
+
for (const block of message.content) {
|
|
356
|
+
if (block.type === "tool_result") {
|
|
357
|
+
out.push({
|
|
358
|
+
role: "toolResult",
|
|
359
|
+
toolCallId: block.toolCallId,
|
|
360
|
+
toolName: block.toolName,
|
|
361
|
+
content: block.content.map(toPiInputContent),
|
|
362
|
+
isError: block.isError ?? false,
|
|
363
|
+
timestamp,
|
|
364
|
+
});
|
|
365
|
+
continue;
|
|
366
|
+
}
|
|
367
|
+
if (block.type === "text" || block.type === "image")
|
|
368
|
+
direct.push(toPiInputContent(block));
|
|
369
|
+
}
|
|
370
|
+
if (direct.length)
|
|
371
|
+
out.push({ role: "user", content: direct, timestamp });
|
|
372
|
+
return out;
|
|
373
|
+
}
|
|
374
|
+
function toPiInputContent(block) {
|
|
375
|
+
return block.type === "text"
|
|
376
|
+
? { type: "text", text: block.text }
|
|
377
|
+
: { type: "image", data: block.data, mimeType: block.mimeType };
|
|
378
|
+
}
|
|
379
|
+
function toPiUsage(usage) {
|
|
380
|
+
return {
|
|
381
|
+
input: usage?.inputTokens ?? 0,
|
|
382
|
+
output: usage?.outputTokens ?? 0,
|
|
383
|
+
cacheRead: usage?.cacheReadTokens ?? 0,
|
|
384
|
+
cacheWrite: usage?.cacheWriteTokens ?? 0,
|
|
385
|
+
totalTokens: (usage?.inputTokens ?? 0) + (usage?.outputTokens ?? 0),
|
|
386
|
+
cost: { input: 0, output: 0, cacheRead: 0, cacheWrite: 0, total: 0 },
|
|
387
|
+
};
|
|
388
|
+
}
|
|
389
|
+
/**
|
|
390
|
+
* Pull the raw credential back out of the resolved headers.
|
|
391
|
+
*
|
|
392
|
+
* The vendor SDKs want a key, not a header, and `AuthResolver` deals only in
|
|
393
|
+
* headers because that is what the wire needs. Rather than widen that
|
|
394
|
+
* contract for one caller, the common carriers are read back here; anything
|
|
395
|
+
* unrecognized still reaches the request as a plain header.
|
|
396
|
+
*/
|
|
397
|
+
function credentialFrom(resolved) {
|
|
398
|
+
if (!resolved)
|
|
399
|
+
return undefined;
|
|
400
|
+
for (const [name, value] of Object.entries(resolved.headers)) {
|
|
401
|
+
const header = name.toLowerCase();
|
|
402
|
+
if (header === "authorization")
|
|
403
|
+
return value.replace(/^Bearer\s+/i, "");
|
|
404
|
+
if (header === "x-api-key" || header === "x-goog-api-key")
|
|
405
|
+
return value;
|
|
406
|
+
}
|
|
407
|
+
return undefined;
|
|
408
|
+
}
|
|
409
|
+
// ---------------------------------------------------------------------------
|
|
410
|
+
// Response translation
|
|
411
|
+
// ---------------------------------------------------------------------------
|
|
412
|
+
/**
|
|
413
|
+
* Fold pi-ai's event protocol into the harness's.
|
|
414
|
+
*
|
|
415
|
+
* The shapes differ in one way that matters: pi-ai indexes events by position
|
|
416
|
+
* in the assistant message and carries the running message on every event,
|
|
417
|
+
* while the harness identifies tool calls by id. The id is only knowable by
|
|
418
|
+
* reading the partial message, and for some providers it is not there on the
|
|
419
|
+
* first event of a call — so `tool_call_start` is emitted as soon as an id and
|
|
420
|
+
* a name exist, not blindly at `toolcall_start`.
|
|
421
|
+
*/
|
|
422
|
+
async function* mapEvents(events, providerId, modelId) {
|
|
423
|
+
const started = new Map();
|
|
424
|
+
for await (const event of events) {
|
|
425
|
+
switch (event.type) {
|
|
426
|
+
case "start":
|
|
427
|
+
yield { type: "start", model: event.partial.model || modelId };
|
|
428
|
+
break;
|
|
429
|
+
case "text_delta":
|
|
430
|
+
yield { type: "text_delta", text: event.delta };
|
|
431
|
+
break;
|
|
432
|
+
case "thinking_delta":
|
|
433
|
+
yield { type: "thinking_delta", text: event.delta };
|
|
434
|
+
break;
|
|
435
|
+
case "thinking_end": {
|
|
436
|
+
const block = event.partial.content[event.contentIndex];
|
|
437
|
+
if (block?.type === "thinking" && block.thinkingSignature) {
|
|
438
|
+
yield { type: "thinking_signature", signature: block.thinkingSignature };
|
|
439
|
+
}
|
|
440
|
+
break;
|
|
441
|
+
}
|
|
442
|
+
case "toolcall_start":
|
|
443
|
+
case "toolcall_delta": {
|
|
444
|
+
const block = event.partial.content[event.contentIndex];
|
|
445
|
+
const call = block?.type === "toolCall" ? block : undefined;
|
|
446
|
+
if (call?.id && call.name && !started.has(event.contentIndex)) {
|
|
447
|
+
started.set(event.contentIndex, call.id);
|
|
448
|
+
yield { type: "tool_call_start", id: call.id, name: call.name };
|
|
449
|
+
}
|
|
450
|
+
if (event.type === "toolcall_delta") {
|
|
451
|
+
const id = started.get(event.contentIndex);
|
|
452
|
+
if (id)
|
|
453
|
+
yield { type: "tool_call_delta", id, argsDelta: event.delta };
|
|
454
|
+
}
|
|
455
|
+
break;
|
|
456
|
+
}
|
|
457
|
+
case "toolcall_end": {
|
|
458
|
+
const { toolCall } = event;
|
|
459
|
+
if (!started.has(event.contentIndex)) {
|
|
460
|
+
// A provider that streams a tool call atomically never gave us an id
|
|
461
|
+
// to announce; the consumer still needs the pair.
|
|
462
|
+
yield { type: "tool_call_start", id: toolCall.id, name: toolCall.name };
|
|
463
|
+
started.set(event.contentIndex, toolCall.id);
|
|
464
|
+
}
|
|
465
|
+
yield {
|
|
466
|
+
type: "tool_call_end",
|
|
467
|
+
id: toolCall.id,
|
|
468
|
+
name: toolCall.name,
|
|
469
|
+
input: toolCall.arguments,
|
|
470
|
+
};
|
|
471
|
+
break;
|
|
472
|
+
}
|
|
473
|
+
case "done":
|
|
474
|
+
yield {
|
|
475
|
+
type: "end",
|
|
476
|
+
stopReason: mapStopReason(event.reason),
|
|
477
|
+
usage: fromPiUsage(event.message.usage),
|
|
478
|
+
};
|
|
479
|
+
break;
|
|
480
|
+
case "error": {
|
|
481
|
+
const message = event.error.errorMessage ?? "the provider stream failed";
|
|
482
|
+
// An abort is the caller's own doing. Surfacing it as a provider
|
|
483
|
+
// failure would send `ResilientProvider` into a restart of a request
|
|
484
|
+
// the user just cancelled.
|
|
485
|
+
if (event.reason === "aborted")
|
|
486
|
+
throw new DOMException(message, "AbortError");
|
|
487
|
+
const status = statusFromMessage(message);
|
|
488
|
+
throw new ProviderError(providerId, message, {
|
|
489
|
+
cause: event.error,
|
|
490
|
+
...(status !== undefined ? { status } : {}),
|
|
491
|
+
// Carried for the caller to read, not to change what gets retried.
|
|
492
|
+
// This path has never retried, and turning every 429 and 5xx into a
|
|
493
|
+
// retry here is a separate decision with its own failure mode.
|
|
494
|
+
retryable: false,
|
|
495
|
+
});
|
|
496
|
+
}
|
|
497
|
+
default:
|
|
498
|
+
break;
|
|
499
|
+
}
|
|
500
|
+
}
|
|
501
|
+
}
|
|
502
|
+
/**
|
|
503
|
+
* The HTTP status behind a stream failure, when the SDK left one legible.
|
|
504
|
+
*
|
|
505
|
+
* The stream's error event carries a string and nothing else — there is no
|
|
506
|
+
* status field on it — and the SDK composes that string as `<status>: <body>`,
|
|
507
|
+
* or `<prefix> (<status>): <body>` for the providers that name themselves.
|
|
508
|
+
* Reading it back is parsing somebody else's format, so it is best effort and
|
|
509
|
+
* nothing is allowed to depend on it being there.
|
|
510
|
+
*
|
|
511
|
+
* It is worth doing for the one caller that acts on it: a 402 from the
|
|
512
|
+
* metering gateway is not an error to print, it is a paywall to open, and
|
|
513
|
+
* without this the difference between "this account is out of credits" and
|
|
514
|
+
* "this key is wrong" exists only inside a sentence.
|
|
515
|
+
*/
|
|
516
|
+
function statusFromMessage(message) {
|
|
517
|
+
const match = /^(?:[^(]*\((\d{3})\)|(\d{3}))\s*:/.exec(message);
|
|
518
|
+
const code = match?.[1] ?? match?.[2];
|
|
519
|
+
if (!code)
|
|
520
|
+
return undefined;
|
|
521
|
+
const status = Number(code);
|
|
522
|
+
return status >= 100 && status <= 599 ? status : undefined;
|
|
523
|
+
}
|
|
524
|
+
function mapStopReason(reason) {
|
|
525
|
+
switch (reason) {
|
|
526
|
+
case "stop":
|
|
527
|
+
return "end_turn";
|
|
528
|
+
case "toolUse":
|
|
529
|
+
return "tool_use";
|
|
530
|
+
case "length":
|
|
531
|
+
return "max_tokens";
|
|
532
|
+
case "aborted":
|
|
533
|
+
return "aborted";
|
|
534
|
+
case "error":
|
|
535
|
+
return "error";
|
|
536
|
+
default:
|
|
537
|
+
return "end_turn";
|
|
538
|
+
}
|
|
539
|
+
}
|
|
540
|
+
function fromPiUsage(usage) {
|
|
541
|
+
if (!usage)
|
|
542
|
+
return emptyUsage();
|
|
543
|
+
return {
|
|
544
|
+
inputTokens: usage.input ?? 0,
|
|
545
|
+
outputTokens: usage.output ?? 0,
|
|
546
|
+
cacheReadTokens: usage.cacheRead ?? 0,
|
|
547
|
+
cacheWriteTokens: usage.cacheWrite ?? 0,
|
|
548
|
+
...(usage.reasoning === undefined ? {} : { reasoningTokens: usage.reasoning }),
|
|
549
|
+
};
|
|
550
|
+
}
|
|
551
|
+
//# sourceMappingURL=piai.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"piai.js","sourceRoot":"","sources":["../../src/providers/piai.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,65 @@
|
|
|
1
|
+
import type { Catalog, CatalogProvider } from "./catalog.ts";
|
|
2
|
+
import type { PiAiProviderOptions } from "./piai.ts";
|
|
3
|
+
import type { AuthResolver } from "../auth/types.ts";
|
|
4
|
+
import type { ModelSpec, Provider, ProviderCredentials } from "./types.ts";
|
|
5
|
+
/**
|
|
6
|
+
* Holds providers and model specs, and resolves the aliases used by `/model`.
|
|
7
|
+
*
|
|
8
|
+
* Model switching lives here rather than in the agent: because conversation
|
|
9
|
+
* history is stored provider-neutrally, changing models is nothing more than
|
|
10
|
+
* resolving a different spec for the next request.
|
|
11
|
+
*/
|
|
12
|
+
export declare class ProviderRegistry {
|
|
13
|
+
private readonly providers;
|
|
14
|
+
private readonly models;
|
|
15
|
+
private catalogProviders;
|
|
16
|
+
/**
|
|
17
|
+
* Build a registry from a catalog.
|
|
18
|
+
*
|
|
19
|
+
* Every provider comes from data — which protocol it speaks, where it lives,
|
|
20
|
+
* which env var holds its key — so adding a vendor never requires a code
|
|
21
|
+
* change, only a catalog entry.
|
|
22
|
+
*/
|
|
23
|
+
static fromCatalog(catalog: Catalog, opts?: {
|
|
24
|
+
creds?: Record<string, ProviderCredentials>;
|
|
25
|
+
auth?: AuthResolver;
|
|
26
|
+
}): ProviderRegistry;
|
|
27
|
+
/** The catalog entry behind a provider, for `/models` and login hints. */
|
|
28
|
+
catalogEntry(id: string): CatalogProvider | undefined;
|
|
29
|
+
listCatalogProviders(): CatalogProvider[];
|
|
30
|
+
registerProvider(provider: Provider): this;
|
|
31
|
+
/** Register an OpenAI-compatible vendor under its own provider id. */
|
|
32
|
+
registerOpenAiCompatible(opts: Omit<PiAiProviderOptions, "api"> & {
|
|
33
|
+
id: string;
|
|
34
|
+
}): this;
|
|
35
|
+
/** Register (or replace) a provider from a catalog entry. */
|
|
36
|
+
registerCatalogProvider(entry: CatalogProvider, creds?: ProviderCredentials): this;
|
|
37
|
+
registerModel(spec: ModelSpec): this;
|
|
38
|
+
getProvider(id: string): Provider;
|
|
39
|
+
/**
|
|
40
|
+
* Resolve an alias (`sonnet`), a wire model id (`claude-sonnet-5`), or a
|
|
41
|
+
* fully qualified `provider/model` reference.
|
|
42
|
+
*/
|
|
43
|
+
resolve(ref: string): ModelSpec;
|
|
44
|
+
/**
|
|
45
|
+
* Models worth showing.
|
|
46
|
+
*
|
|
47
|
+
* Aliases are excluded: they resolve, but they are the same model under a
|
|
48
|
+
* shorter name, and listing both turns a discovered roster of 300 into 600.
|
|
49
|
+
*/
|
|
50
|
+
listModels(opts?: {
|
|
51
|
+
configuredOnly?: boolean;
|
|
52
|
+
includeAliases?: boolean;
|
|
53
|
+
}): ModelSpec[];
|
|
54
|
+
listProviders(): Provider[];
|
|
55
|
+
hasModel(id: string): boolean;
|
|
56
|
+
/**
|
|
57
|
+
* Ask providers that support it which models the account can actually use,
|
|
58
|
+
* and merge the results into the catalog.
|
|
59
|
+
*
|
|
60
|
+
* Subscription plans gate models by entitlement, so a static catalog will
|
|
61
|
+
* happily offer something the account cannot call. Returns the ids added or
|
|
62
|
+
* updated.
|
|
63
|
+
*/
|
|
64
|
+
refreshModels(providerId?: string): Promise<ModelSpec[]>;
|
|
65
|
+
}
|