Skip to content

Commit 1b01ec1

Browse files
authored
feat(gateway): add providerTimeouts to provider options (#13015)
1 parent b1a8425 commit 1b01ec1

File tree

4 files changed

+79
-0
lines changed

4 files changed

+79
-0
lines changed

.changeset/quick-lemons-sleep.md

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
---
2+
'@ai-sdk/gateway': patch
3+
---
4+
5+
feat(gateway): add providerTimeouts to provider options

content/providers/01-ai-sdk-providers/00-ai-gateway.mdx

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -631,6 +631,14 @@ The following gateway provider options are available:
631631

632632
Restricts routing requests to providers that have zero data retention policies.
633633

634+
- **providerTimeouts** _object_
635+
636+
Per-provider timeouts for BYOK credentials in milliseconds. Controls how long to wait for a provider to start responding before falling back to the next available provider.
637+
638+
Example: `providerTimeouts: { byok: { openai: 5000, anthropic: 2000 } }`
639+
640+
For full details, see [Provider Timeouts](https://vercel.com/docs/ai-gateway/models-and-providers/provider-timeouts).
641+
634642
You can combine these options to have fine-grained control over routing and tracking:
635643

636644
```ts

packages/gateway/src/gateway-language-model.test.ts

Lines changed: 54 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1481,5 +1481,59 @@ describe('GatewayLanguageModel', () => {
14811481
gateway: { order: ['anthropic', 'bedrock', 'openai'] },
14821482
});
14831483
});
1484+
1485+
it('should pass providerTimeouts for doGenerate', async () => {
1486+
prepareJsonResponse({
1487+
content: { type: 'text', text: 'Test response' },
1488+
});
1489+
1490+
await createTestModel().doGenerate({
1491+
prompt: TEST_PROMPT,
1492+
providerOptions: {
1493+
gateway: {
1494+
providerTimeouts: {
1495+
byok: { openai: 5000, anthropic: 2000 },
1496+
},
1497+
},
1498+
},
1499+
});
1500+
1501+
const requestBody = await server.calls[0].requestBodyJson;
1502+
expect(requestBody.providerOptions).toEqual({
1503+
gateway: {
1504+
providerTimeouts: {
1505+
byok: { openai: 5000, anthropic: 2000 },
1506+
},
1507+
},
1508+
});
1509+
});
1510+
1511+
it('should pass providerTimeouts for doStream', async () => {
1512+
prepareStreamResponse({
1513+
content: ['Hello', ' world'],
1514+
});
1515+
1516+
const { stream } = await createTestModel().doStream({
1517+
prompt: TEST_PROMPT,
1518+
providerOptions: {
1519+
gateway: {
1520+
providerTimeouts: {
1521+
byok: { anthropic: 3000 },
1522+
},
1523+
},
1524+
},
1525+
});
1526+
1527+
await convertReadableStreamToArray(stream);
1528+
1529+
const requestBody = await server.calls[0].requestBodyJson;
1530+
expect(requestBody.providerOptions).toEqual({
1531+
gateway: {
1532+
providerTimeouts: {
1533+
byok: { anthropic: 3000 },
1534+
},
1535+
},
1536+
});
1537+
});
14841538
});
14851539
});

packages/gateway/src/gateway-provider-options.ts

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -59,6 +59,18 @@ const gatewayLanguageModelOptions = lazySchema(() =>
5959
* used.
6060
*/
6161
zeroDataRetention: z.boolean().optional(),
62+
/**
63+
* Per-provider timeouts for BYOK credentials in milliseconds.
64+
* Controls how long to wait for a provider to start responding
65+
* before falling back to the next available provider.
66+
*
67+
* Example: `{ byok: { openai: 5000, anthropic: 2000 } }`
68+
*/
69+
providerTimeouts: z
70+
.object({
71+
byok: z.record(z.string(), z.number().int().min(1000)).optional(),
72+
})
73+
.optional(),
6274
}),
6375
),
6476
);

0 commit comments

Comments
 (0)