-
Notifications
You must be signed in to change notification settings - Fork 784
feat(xai): enable Priority (Fast) on the API-key transport only #1885
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: dev
Are you sure you want to change the base?
Changes from all commits
8f9e99b
abf3227
c1a6c4d
be8a64c
cad44ea
9721126
e022e2e
c89af62
8d7879e
e0eeeb8
43f7c4d
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change | ||||||||||||||||||||||||||||||||||||||||||||||||
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
|
|
@@ -6,6 +6,14 @@ import { getProviderRegistryEntry, providerModelWireDefault, type InboundWire } | |||||||||||||||||||||||||||||||||||||||||||||||||
| export const SERVICE_TIER_ADAPTERS = new Set(["openai-chat", "openai-responses"]); | ||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||||||||||
| export type CapturedServiceTierAdapterAuthority = Readonly<Record<string, string>>; | ||||||||||||||||||||||||||||||||||||||||||||||||||
| /** | ||||||||||||||||||||||||||||||||||||||||||||||||||
| * xAI multiplexes two transports under one provider id: an API-key mode that stays on | ||||||||||||||||||||||||||||||||||||||||||||||||||
| * https://api.x.ai/v1 (where Priority Processing is documented) and an OAuth/CLI mode that | ||||||||||||||||||||||||||||||||||||||||||||||||||
| * resolves to https://cli-chat-proxy.grok.com/v1 (unverified by public docs). The built-in | ||||||||||||||||||||||||||||||||||||||||||||||||||
| * xai preset opts into chatServiceTier, but that opt-in must only arm when the effective | ||||||||||||||||||||||||||||||||||||||||||||||||||
| * transport is the canonical API-key path (issue #1875). | ||||||||||||||||||||||||||||||||||||||||||||||||||
| */ | ||||||||||||||||||||||||||||||||||||||||||||||||||
| const XAI_CHAT_PRIORITY_PROVIDER = "xai"; | ||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||||||||||
| const capturedAdapterAuthority = new WeakMap<object, CapturedServiceTierAdapterAuthority>(); | ||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
@@ -14,6 +22,11 @@ type ServiceTierCapabilityProvider = Pick< | |||||||||||||||||||||||||||||||||||||||||||||||||
| "adapter" | "supportsServiceTier" | "modelSupportsServiceTier" | "modelAdapters" | "baseUrl" | "authMode" | "chatServiceTier" | ||||||||||||||||||||||||||||||||||||||||||||||||||
| >; | ||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||||||||||
| type ChatServiceTierProvider = Pick< | ||||||||||||||||||||||||||||||||||||||||||||||||||
| OcxProviderConfig, | ||||||||||||||||||||||||||||||||||||||||||||||||||
| "supportsServiceTier" | "modelSupportsServiceTier" | "chatServiceTier" | ||||||||||||||||||||||||||||||||||||||||||||||||||
| > & Partial<Pick<OcxProviderConfig, "adapter" | "baseUrl" | "authMode">>; | ||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||||||||||
| /** | ||||||||||||||||||||||||||||||||||||||||||||||||||
| * Read a model map by exact model identity. Service-tier capability is deliberately | ||||||||||||||||||||||||||||||||||||||||||||||||||
| * stricter than the older model metadata maps: a family key or a colon-qualified | ||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
@@ -34,6 +47,29 @@ function exactModelValue<T>( | |||||||||||||||||||||||||||||||||||||||||||||||||
| return undefined; | ||||||||||||||||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||||||||||
| function isXaiPriorityProvider(providerName: string | undefined): boolean { | ||||||||||||||||||||||||||||||||||||||||||||||||||
| return providerName?.trim().toLowerCase() === XAI_CHAT_PRIORITY_PROVIDER; | ||||||||||||||||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||||||||||
| function isCanonicalXaiPriorityTransport(provider: ChatServiceTierProvider): boolean { | ||||||||||||||||||||||||||||||||||||||||||||||||||
| if (provider.authMode !== "key") return false; | ||||||||||||||||||||||||||||||||||||||||||||||||||
| if (provider.adapter?.trim().toLowerCase() !== "openai-chat") return false; | ||||||||||||||||||||||||||||||||||||||||||||||||||
| if (typeof provider.baseUrl !== "string") return false; | ||||||||||||||||||||||||||||||||||||||||||||||||||
| try { | ||||||||||||||||||||||||||||||||||||||||||||||||||
| const url = new URL(provider.baseUrl.trim()); | ||||||||||||||||||||||||||||||||||||||||||||||||||
| return url.protocol === "https:" | ||||||||||||||||||||||||||||||||||||||||||||||||||
| && url.username === "" | ||||||||||||||||||||||||||||||||||||||||||||||||||
| && url.password === "" | ||||||||||||||||||||||||||||||||||||||||||||||||||
| && url.hostname.toLowerCase() === "api.x.ai" | ||||||||||||||||||||||||||||||||||||||||||||||||||
| && url.port === "" | ||||||||||||||||||||||||||||||||||||||||||||||||||
| && (url.pathname === "/v1" || url.pathname === "/v1/") | ||||||||||||||||||||||||||||||||||||||||||||||||||
| && url.search === "" | ||||||||||||||||||||||||||||||||||||||||||||||||||
| && url.hash === ""; | ||||||||||||||||||||||||||||||||||||||||||||||||||
|
Comment on lines
+57
to
+67
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 🎯 Functional Correctness | 🟡 Minor | ⚡ Quick win Reject explicit default-port URLs before URL normalization. Line 64 accepts Validate the raw authority before parsing, or otherwise detect an explicit port. Add Proposed fix- const url = new URL(provider.baseUrl.trim());
+ const input = provider.baseUrl.trim();
+ if (!/^https:\/\/api\.x\.ai(?:\/|$)/i.test(input)) return false;
+ const url = new URL(input);📝 Committable suggestion
Suggested change
🤖 Prompt for AI Agents |
||||||||||||||||||||||||||||||||||||||||||||||||||
| } catch { | ||||||||||||||||||||||||||||||||||||||||||||||||||
| return false; | ||||||||||||||||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||||||||||
| /** | ||||||||||||||||||||||||||||||||||||||||||||||||||
| * Resolve the declared provider/model capability. An explicit provider-level false is a | ||||||||||||||||||||||||||||||||||||||||||||||||||
| * fail-closed boundary and cannot be reopened by a model map. Otherwise an exact model | ||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
@@ -50,13 +86,19 @@ export function supportsServiceTierForModel( | |||||||||||||||||||||||||||||||||||||||||||||||||
| ?? provider.supportsServiceTier; | ||||||||||||||||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||||||||||
| /** Whether the Chat serializer may emit a tier for this exact model. */ | ||||||||||||||||||||||||||||||||||||||||||||||||||
| /** Whether the Chat serializer may emit a tier for this exact model and effective transport. */ | ||||||||||||||||||||||||||||||||||||||||||||||||||
| export function canSerializeServiceTierForChatModel( | ||||||||||||||||||||||||||||||||||||||||||||||||||
| provider: Pick<OcxProviderConfig, "supportsServiceTier" | "modelSupportsServiceTier" | "chatServiceTier">, | ||||||||||||||||||||||||||||||||||||||||||||||||||
| provider: ChatServiceTierProvider, | ||||||||||||||||||||||||||||||||||||||||||||||||||
| modelId: string, | ||||||||||||||||||||||||||||||||||||||||||||||||||
| providerName?: string, | ||||||||||||||||||||||||||||||||||||||||||||||||||
| ): boolean { | ||||||||||||||||||||||||||||||||||||||||||||||||||
| const exact = exactModelValue(provider.modelSupportsServiceTier, modelId); | ||||||||||||||||||||||||||||||||||||||||||||||||||
| if (provider.supportsServiceTier === false || exact === false) return false; | ||||||||||||||||||||||||||||||||||||||||||||||||||
| if (provider.supportsServiceTier === false || provider.chatServiceTier === false || exact === false) { | ||||||||||||||||||||||||||||||||||||||||||||||||||
| return false; | ||||||||||||||||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||||||||||||||||
| if (isXaiPriorityProvider(providerName) && !isCanonicalXaiPriorityTransport(provider)) { | ||||||||||||||||||||||||||||||||||||||||||||||||||
| return false; | ||||||||||||||||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||||||||||||||||
| return provider.chatServiceTier === true || exact === true; | ||||||||||||||||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
@@ -135,9 +177,17 @@ export function serviceTierSupportForModel( | |||||||||||||||||||||||||||||||||||||||||||||||||
| ? provider.adapter | ||||||||||||||||||||||||||||||||||||||||||||||||||
| : serviceTierAdapterForModel(providerName, provider, modelId, inbound); | ||||||||||||||||||||||||||||||||||||||||||||||||||
| if (!SERVICE_TIER_ADAPTERS.has(adapter)) return false; | ||||||||||||||||||||||||||||||||||||||||||||||||||
| // xAI Fast is verified only on its canonical API-key Chat transport. Keep every other xAI | ||||||||||||||||||||||||||||||||||||||||||||||||||
| // wire fail-closed even if it happens to use another OpenAI-compatible adapter. | ||||||||||||||||||||||||||||||||||||||||||||||||||
| if (isXaiPriorityProvider(providerName)) { | ||||||||||||||||||||||||||||||||||||||||||||||||||
| if (adapter !== "openai-chat") return false; | ||||||||||||||||||||||||||||||||||||||||||||||||||
| return canSerializeServiceTierForChatModel(provider, modelId, providerName) ? true : false; | ||||||||||||||||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||||||||||||||||
| // Treat the Chat serializer decision as authoritative so catalog metadata, routing | ||||||||||||||||||||||||||||||||||||||||||||||||||
| // evidence, fast-mode injection, and caller-tier stripping cannot claim support that the | ||||||||||||||||||||||||||||||||||||||||||||||||||
| // final request builder will omit. A provider-wide false and an exact false stay closed. | ||||||||||||||||||||||||||||||||||||||||||||||||||
| if (adapter === "openai-chat" && !canSerializeServiceTierForChatModel(provider, modelId)) return false; | ||||||||||||||||||||||||||||||||||||||||||||||||||
| // final request builder will omit. | ||||||||||||||||||||||||||||||||||||||||||||||||||
| if (adapter === "openai-chat") { | ||||||||||||||||||||||||||||||||||||||||||||||||||
| return canSerializeServiceTierForChatModel(provider, modelId, providerName) ? true : false; | ||||||||||||||||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||||||||||||||||
| return supportsServiceTierForModel(provider, modelId); | ||||||||||||||||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||||||||||||||||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
🎯 Functional Correctness | 🟡 Minor | ⚡ Quick win
Preserve the default key authentication mode.
Line 55 rejects a canonical xAI API-key configuration when
authModeis omitted.OcxProviderConfig.authModeis optional and documents"key"as its default. This configuration cannot serializeservice_tier: "priority".Treat an omitted
authModeas key mode. Continue to reject every explicit non-key mode. Add a regression case withauthMode: undefined.Proposed fix
function isCanonicalXaiPriorityTransport(provider: ChatServiceTierProvider): boolean { - if (provider.authMode !== "key") return false; + if (provider.authMode !== undefined && provider.authMode !== "key") return false; if (provider.adapter?.trim().toLowerCase() !== "openai-chat") return false;📝 Committable suggestion
🤖 Prompt for AI Agents