@oh-my-pi/pi-catalog 18.4.3 → 18.4.4
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/CHANGELOG.md +17 -0
- package/dist/types/compat/anthropic.d.ts +6 -0
- package/dist/types/hosts.d.ts +13 -0
- package/dist/types/types.d.ts +29 -1
- package/dist/types/wire/codex.d.ts +5 -3
- package/package.json +4 -4
- package/src/compat/anthropic.ts +11 -1
- package/src/compat/axes.ts +2 -0
- package/src/compat/resolve.ts +13 -3
- package/src/compat/rules/classes/anthropic.kdl +7 -3
- package/src/compat/rules/providers/openai-codex.kdl +17 -0
- package/src/compat/rules.json +1 -1
- package/src/discovery/codex.ts +16 -0
- package/src/hosts.ts +47 -0
- package/src/models.json +1 -1
- package/src/types.ts +31 -1
- package/src/wire/codex.ts +5 -3
package/src/discovery/codex.ts
CHANGED
|
@@ -71,6 +71,7 @@ const codexModelEntrySchema = type({
|
|
|
71
71
|
"use_responses_lite?": "unknown",
|
|
72
72
|
"tool_mode?": "unknown",
|
|
73
73
|
"available_access_programs?": "unknown",
|
|
74
|
+
"service_tiers?": "unknown",
|
|
74
75
|
});
|
|
75
76
|
|
|
76
77
|
const codexModelsResponseSchema = type({
|
|
@@ -303,6 +304,8 @@ interface ParsedCodexModelEntry {
|
|
|
303
304
|
useResponsesLite: boolean;
|
|
304
305
|
toolMode: boolean;
|
|
305
306
|
priority: number;
|
|
307
|
+
/** Advertised tier ids; `undefined` when the entry has no `service_tiers` array. */
|
|
308
|
+
serviceTiers: string[] | undefined;
|
|
306
309
|
}
|
|
307
310
|
|
|
308
311
|
function parseCodexModelEntry(entry: unknown): ParsedCodexModelEntry | null {
|
|
@@ -332,6 +335,17 @@ function parseCodexModelEntry(entry: unknown): ParsedCodexModelEntry | null {
|
|
|
332
335
|
}
|
|
333
336
|
}
|
|
334
337
|
|
|
338
|
+
// codex-rs `ModelServiceTier { id, name, description }`; only the id reaches the wire.
|
|
339
|
+
// An explicit empty array is kept: it means the model offers no optional tier.
|
|
340
|
+
let serviceTiers: string[] | undefined;
|
|
341
|
+
if (Array.isArray(payload.service_tiers)) {
|
|
342
|
+
serviceTiers = [];
|
|
343
|
+
for (const tier of payload.service_tiers) {
|
|
344
|
+
const id = tier !== null && typeof tier === "object" && "id" in tier ? toNonEmptyString(tier.id) : null;
|
|
345
|
+
if (id && !serviceTiers.includes(id)) serviceTiers.push(id);
|
|
346
|
+
}
|
|
347
|
+
}
|
|
348
|
+
|
|
335
349
|
return {
|
|
336
350
|
slug,
|
|
337
351
|
cyberPrograms,
|
|
@@ -344,6 +358,7 @@ function parseCodexModelEntry(entry: unknown): ParsedCodexModelEntry | null {
|
|
|
344
358
|
useResponsesLite: toBoolean(payload.use_responses_lite) === true,
|
|
345
359
|
toolMode: payload.tool_mode === "code_mode_only",
|
|
346
360
|
priority: toFiniteNumber(payload.priority) ?? Number.MAX_SAFE_INTEGER,
|
|
361
|
+
serviceTiers,
|
|
347
362
|
};
|
|
348
363
|
}
|
|
349
364
|
|
|
@@ -408,6 +423,7 @@ function buildNormalizedCodexModel(
|
|
|
408
423
|
...(parsed.preferWebsockets ? { preferWebsockets: true } : {}),
|
|
409
424
|
...(parsed.useResponsesLite ? { useResponsesLite: true } : {}),
|
|
410
425
|
...(parsed.toolMode ? { toolMode: "code_mode_only" as const } : {}),
|
|
426
|
+
...(parsed.serviceTiers !== undefined ? { serviceTiers: parsed.serviceTiers } : {}),
|
|
411
427
|
...(parsed.priority !== Number.MAX_SAFE_INTEGER ? { priority: parsed.priority } : {}),
|
|
412
428
|
},
|
|
413
429
|
};
|
package/src/hosts.ts
CHANGED
|
@@ -169,6 +169,53 @@ export function isAzureDeploymentsUrl(baseUrl: string): boolean {
|
|
|
169
169
|
return baseUrl.includes("/deployments/");
|
|
170
170
|
}
|
|
171
171
|
|
|
172
|
+
// Bedrock inference endpoints, per AWS's endpoint and PrivateLink docs:
|
|
173
|
+
// - bedrock-runtime: `bedrock-runtime.<region>.amazonaws.com`, FIPS `bedrock-runtime-fips.<region>.amazonaws.com`
|
|
174
|
+
// - bedrock-mantle: `bedrock-mantle.<region>.api.aws`; the bundled provider keeps a `{region}`
|
|
175
|
+
// template until request preparation fills it in
|
|
176
|
+
// - PrivateLink endpoint-specific names for either service, Regional or zonal:
|
|
177
|
+
// `<vpce-id>[-<az>].<service>.<region>.vpce.amazonaws.com`
|
|
178
|
+
// With private DNS enabled, a VPC endpoint answers on the public names above.
|
|
179
|
+
const BEDROCK_PUBLIC_HOST =
|
|
180
|
+
/^(?:(?<runtime>bedrock-runtime(?:-fips)?)\.[a-z0-9-]+\.amazonaws\.com|bedrock-mantle\.(?:[a-z0-9-]+|\{region\})\.api\.aws)$/;
|
|
181
|
+
const BEDROCK_PRIVATELINK_HOST =
|
|
182
|
+
/^vpce-[a-z0-9-]+\.(?:(?<runtime>bedrock-runtime(?:-fips)?)|bedrock-mantle)\.[a-z0-9-]+\.vpce\.amazonaws\.com$/;
|
|
183
|
+
|
|
184
|
+
function hasPathPrefix(pathname: string, prefix: string): boolean {
|
|
185
|
+
return pathname === prefix || pathname.startsWith(`${prefix}/`);
|
|
186
|
+
}
|
|
187
|
+
|
|
188
|
+
/**
|
|
189
|
+
* Amazon Bedrock API route on a bedrock-runtime or bedrock-mantle endpoint
|
|
190
|
+
* (public, FIPS, or PrivateLink hostname):
|
|
191
|
+
* - `anthropic`: the Anthropic Messages API under `/anthropic`.
|
|
192
|
+
* - `openai`: the OpenAI-compatible APIs under `/openai`, plus Mantle's
|
|
193
|
+
* documented `/v1` base (`https://bedrock-mantle.<region>.api.aws/v1`).
|
|
194
|
+
*
|
|
195
|
+
* Hostnames are parsed strictly so proxies that embed these hosts in a path
|
|
196
|
+
* do not match.
|
|
197
|
+
*/
|
|
198
|
+
export function isBedrockRouteUrl(baseUrl: string | undefined, route: "openai" | "anthropic"): boolean {
|
|
199
|
+
if (!baseUrl) return false;
|
|
200
|
+
let url: URL;
|
|
201
|
+
try {
|
|
202
|
+
url = new URL(baseUrl);
|
|
203
|
+
} catch {
|
|
204
|
+
return false;
|
|
205
|
+
}
|
|
206
|
+
if (url.protocol !== "https:") return false;
|
|
207
|
+
const host = BEDROCK_PUBLIC_HOST.exec(url.hostname) ?? BEDROCK_PRIVATELINK_HOST.exec(url.hostname);
|
|
208
|
+
if (!host) return false;
|
|
209
|
+
if (route === "anthropic") return hasPathPrefix(url.pathname, "/anthropic");
|
|
210
|
+
const isMantle = host.groups?.runtime === undefined;
|
|
211
|
+
return hasPathPrefix(url.pathname, "/openai") || (isMantle && hasPathPrefix(url.pathname, "/v1"));
|
|
212
|
+
}
|
|
213
|
+
|
|
214
|
+
/** Amazon Bedrock's OpenAI-compatible routes; see {@link isBedrockRouteUrl}. */
|
|
215
|
+
export function isBedrockOpenAIUrl(baseUrl: string | undefined): boolean {
|
|
216
|
+
return isBedrockRouteUrl(baseUrl, "openai");
|
|
217
|
+
}
|
|
218
|
+
|
|
172
219
|
/** Alibaba DashScope consumer `compatible-mode` endpoint (rejects multimodal arrays for some text-only SKUs). */
|
|
173
220
|
export function isDashscopeCompatibleModeUrl(baseUrl: string): boolean {
|
|
174
221
|
const normalized = baseUrl.toLowerCase();
|