ollama-ai-provider-v2 1.6.0-beta.0 → 2.0.0-beta.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/README.md +156 -9
- package/dist/index.d.mts +4 -15
- package/dist/index.d.ts +4 -15
- package/dist/index.js +111 -87
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +113 -89
- package/dist/index.mjs.map +1 -1
- package/package.json +9 -5
package/README.md
CHANGED
|
@@ -7,6 +7,20 @@ Use Ollama with the Vercel AI SDK, implementing the official Ollama API. This pr
|
|
|
7
7
|
[](https://nodejs.org/)
|
|
8
8
|
[](https://opensource.org/licenses/Apache-2.0)
|
|
9
9
|
|
|
10
|
+
## 🎉 AI SDK 6 Beta Support
|
|
11
|
+
|
|
12
|
+
This provider now supports **AI SDK 6 Beta** features including:
|
|
13
|
+
|
|
14
|
+
- **🤖 Agent Abstraction** - Build complex agents with `ToolLoopAgent`
|
|
15
|
+
- **🔐 Tool Approval** - Request user confirmation before executing tools
|
|
16
|
+
- **📊 Structured Output** - Generate typed data alongside tool calling
|
|
17
|
+
- **⚡ Enhanced Performance** - Optimized for the latest AI SDK features
|
|
18
|
+
|
|
19
|
+
```bash
|
|
20
|
+
# Install AI SDK 6 Beta + Ollama Provider
|
|
21
|
+
npm install ai@beta ollama-ai-provider-v2
|
|
22
|
+
```
|
|
23
|
+
|
|
10
24
|
## Why Choose Ollama Provider V2?
|
|
11
25
|
|
|
12
26
|
- ✅ **Minimal Dependencies** - Lean codebase with just 2 core dependencies
|
|
@@ -82,19 +96,11 @@ const { text, toolCalls } = await generateText({
|
|
|
82
96
|
Unique feature for models that support chain-of-thought reasoning:
|
|
83
97
|
|
|
84
98
|
```typescript
|
|
85
|
-
// For most models - simple boolean
|
|
86
99
|
const { text } = await generateText({
|
|
87
100
|
model: ollama('deepseek-r1:7b'),
|
|
88
101
|
providerOptions: { ollama: { think: true } },
|
|
89
102
|
prompt: 'Solve this complex math problem step by step: 2x + 5 = 17',
|
|
90
103
|
});
|
|
91
|
-
|
|
92
|
-
// For GPT-OSS models - use thinking levels for trace length control
|
|
93
|
-
const { text } = await generateText({
|
|
94
|
-
model: ollama('gpt-oss:7b'),
|
|
95
|
-
providerOptions: { ollama: { think: 'high' } }, // 'low', 'medium', or 'high'
|
|
96
|
-
prompt: 'Analyze this complex scenario in detail',
|
|
97
|
-
});
|
|
98
104
|
```
|
|
99
105
|
|
|
100
106
|
### Advanced Ollama Options
|
|
@@ -182,7 +188,7 @@ Works with any model in your Ollama installation, including:
|
|
|
182
188
|
|
|
183
189
|
- **Chat Models**: `llama3.2`, `mistral`, `phi4-mini`, `qwen2.5`, `codellama`, `gemma3`
|
|
184
190
|
- **Vision Models**: `llava`, `llama3.2-vision`, `minicpm-v`
|
|
185
|
-
- **Reasoning Models**: `deepseek-r1:7b`, `deepseek-r1:1.5b`, `deepseek-r1:8b
|
|
191
|
+
- **Reasoning Models**: `deepseek-r1:7b`, `deepseek-r1:1.5b`, `deepseek-r1:8b`
|
|
186
192
|
- **Code Models**: `codellama:code`, `codellama:python`, `deepseek-coder-v2`
|
|
187
193
|
- **Embedding Models**: `nomic-embed-text`, `all-minilm`, `mxbai-embed-large`
|
|
188
194
|
|
|
@@ -200,6 +206,147 @@ ollama serve
|
|
|
200
206
|
ollama pull llama3.2
|
|
201
207
|
```
|
|
202
208
|
|
|
209
|
+
# AI SDK 6 Beta examples
|
|
210
|
+
## Agent Abstraction
|
|
211
|
+
|
|
212
|
+
AI SDK 6 introduces the `ToolLoopAgent` class for building agents with full control over execution flow.
|
|
213
|
+
|
|
214
|
+
### Basic Agent
|
|
215
|
+
|
|
216
|
+
```typescript
|
|
217
|
+
import { ToolLoopAgent } from 'ai';
|
|
218
|
+
import { ollama } from 'ollama-ai-provider-v2';
|
|
219
|
+
|
|
220
|
+
const weatherAgent = new ToolLoopAgent({
|
|
221
|
+
model: ollama('llama3.3:70b'),
|
|
222
|
+
instructions: 'You are a helpful weather assistant.',
|
|
223
|
+
tools: {
|
|
224
|
+
weather: weatherTool,
|
|
225
|
+
},
|
|
226
|
+
});
|
|
227
|
+
|
|
228
|
+
const result = await weatherAgent.generate({
|
|
229
|
+
prompt: 'What is the weather in San Francisco?',
|
|
230
|
+
});
|
|
231
|
+
```
|
|
232
|
+
|
|
233
|
+
### Agent with Call Options
|
|
234
|
+
|
|
235
|
+
Use call options to pass runtime configuration to agents:
|
|
236
|
+
|
|
237
|
+
```typescript
|
|
238
|
+
import { ToolLoopAgent } from 'ai';
|
|
239
|
+
import { ollama } from 'ollama-ai-provider-v2';
|
|
240
|
+
import { z } from 'zod';
|
|
241
|
+
|
|
242
|
+
const supportAgent = new ToolLoopAgent({
|
|
243
|
+
model: ollama('qwen2.5:32b'),
|
|
244
|
+
callOptionsSchema: z.object({
|
|
245
|
+
userId: z.string(),
|
|
246
|
+
accountType: z.enum(['free', 'pro', 'enterprise']),
|
|
247
|
+
}),
|
|
248
|
+
instructions: 'You are a helpful customer support agent.',
|
|
249
|
+
prepareCall: ({ options, ...settings }) => ({
|
|
250
|
+
...settings,
|
|
251
|
+
instructions: `${settings.instructions}
|
|
252
|
+
|
|
253
|
+
User context:
|
|
254
|
+
- Account type: ${options.accountType}
|
|
255
|
+
- User ID: ${options.userId}
|
|
256
|
+
|
|
257
|
+
Adjust your response based on the user's account level.`,
|
|
258
|
+
}),
|
|
259
|
+
});
|
|
260
|
+
|
|
261
|
+
const result = await supportAgent.generate({
|
|
262
|
+
prompt: 'How do I upgrade my account?',
|
|
263
|
+
options: {
|
|
264
|
+
userId: 'user_123',
|
|
265
|
+
accountType: 'free',
|
|
266
|
+
},
|
|
267
|
+
});
|
|
268
|
+
```
|
|
269
|
+
|
|
270
|
+
## Tool Execution Approval
|
|
271
|
+
|
|
272
|
+
AI SDK 6 allows you to require user approval before executing tools.
|
|
273
|
+
|
|
274
|
+
### Basic Tool Approval
|
|
275
|
+
|
|
276
|
+
```typescript
|
|
277
|
+
import { tool } from 'ai';
|
|
278
|
+
import { z } from 'zod';
|
|
279
|
+
|
|
280
|
+
export const weatherTool = tool({
|
|
281
|
+
description: 'Get the weather in a location',
|
|
282
|
+
inputSchema: z.object({
|
|
283
|
+
city: z.string(),
|
|
284
|
+
}),
|
|
285
|
+
needsApproval: true, // Always require approval
|
|
286
|
+
execute: async ({ city }) => {
|
|
287
|
+
const weather = await fetchWeather(city);
|
|
288
|
+
return weather;
|
|
289
|
+
},
|
|
290
|
+
});
|
|
291
|
+
```
|
|
292
|
+
|
|
293
|
+
### Dynamic Approval
|
|
294
|
+
|
|
295
|
+
Make approval decisions based on tool input:
|
|
296
|
+
|
|
297
|
+
```typescript
|
|
298
|
+
export const paymentTool = tool({
|
|
299
|
+
description: 'Process a payment',
|
|
300
|
+
inputSchema: z.object({
|
|
301
|
+
amount: z.number(),
|
|
302
|
+
recipient: z.string(),
|
|
303
|
+
}),
|
|
304
|
+
needsApproval: async ({ amount }) => amount > 1000, // Only large payments
|
|
305
|
+
execute: async ({ amount, recipient }) => {
|
|
306
|
+
return await processPayment(amount, recipient);
|
|
307
|
+
},
|
|
308
|
+
});
|
|
309
|
+
```
|
|
310
|
+
|
|
311
|
+
## UI Integration
|
|
312
|
+
|
|
313
|
+
### Server-side API Route
|
|
314
|
+
|
|
315
|
+
```typescript
|
|
316
|
+
import { createAgentUIStreamResponse } from 'ai';
|
|
317
|
+
import { weatherAgent } from '@/lib/agents';
|
|
318
|
+
|
|
319
|
+
export async function POST(request: Request) {
|
|
320
|
+
const { messages } = await request.json();
|
|
321
|
+
|
|
322
|
+
return createAgentUIStreamResponse({
|
|
323
|
+
agent: weatherAgent,
|
|
324
|
+
messages,
|
|
325
|
+
});
|
|
326
|
+
}
|
|
327
|
+
```
|
|
328
|
+
|
|
329
|
+
### Client-side with Type Safety
|
|
330
|
+
|
|
331
|
+
```typescript
|
|
332
|
+
import { useChat } from '@ai-sdk/react';
|
|
333
|
+
import { InferAgentUIMessage } from 'ai';
|
|
334
|
+
import { weatherAgent } from '@/lib/agents';
|
|
335
|
+
|
|
336
|
+
type WeatherAgentUIMessage = InferAgentUIMessage<typeof weatherAgent>;
|
|
337
|
+
|
|
338
|
+
export function WeatherChat() {
|
|
339
|
+
const { messages, sendMessage } = useChat<WeatherAgentUIMessage>();
|
|
340
|
+
|
|
341
|
+
return (
|
|
342
|
+
<div>
|
|
343
|
+
{/* Your chat UI */}
|
|
344
|
+
</div>
|
|
345
|
+
);
|
|
346
|
+
}
|
|
347
|
+
```
|
|
348
|
+
|
|
349
|
+
|
|
203
350
|
## Contributing
|
|
204
351
|
|
|
205
352
|
Contributions are welcome! Here's how to get started:
|
package/dist/index.d.mts
CHANGED
|
@@ -4,11 +4,7 @@ import { z } from 'zod/v4';
|
|
|
4
4
|
|
|
5
5
|
type OllamaChatModelId = "athene-v2" | "athene-v2:72b" | "aya-expanse" | "aya-expanse:8b" | "aya-expanse:32b" | "codegemma" | "codegemma:2b" | "codegemma:7b" | "codellama" | "codellama:7b" | "codellama:13b" | "codellama:34b" | "codellama:70b" | "codellama:code" | "codellama:python" | "command-r" | "command-r:35b" | "command-r-plus" | "command-r-plus:104b" | "command-r7b" | "command-r7b:7b" | "deepseek-r1" | "deepseek-r1:1.5b" | "deepseek-r1:7b" | "deepseek-r1:8b" | "deepseek-r1:14b" | "deepseek-r1:32b" | "deepseek-r1:70b" | "deepseek-r1:671b" | "deepseek-coder-v2" | "deepseek-coder-v2:16b" | "deepseek-coder-v2:236b" | "deepseek-v3" | "deepseek-v3:671b" | "devstral" | "devstral:24b" | "dolphin3" | "dolphin3:8b" | "exaone3.5" | "exaone3.5:2.4b" | "exaone3.5:7.8b" | "exaone3.5:32b" | "falcon2" | "falcon2:11b" | "falcon3" | "falcon3:1b" | "falcon3:3b" | "falcon3:7b" | "falcon3:10b" | "firefunction-v2" | "firefunction-v2:70b" | "gemma" | "gemma:2b" | "gemma:7b" | "gemma2" | "gemma2:2b" | "gemma2:9b" | "gemma2:27b" | "gemma3" | "gemma3:1b" | "gemma3:4b" | "gemma3:12b" | "gemma3:27b" | "granite3-dense" | "granite3-dense:2b" | "granite3-dense:8b" | "granite3-guardian" | "granite3-guardian:2b" | "granite3-guardian:8b" | "granite3-moe" | "granite3-moe:1b" | "granite3-moe:3b" | "granite3.1-dense" | "granite3.1-dense:2b" | "granite3.1-dense:8b" | "granite3.1-moe" | "granite3.1-moe:1b" | "granite3.1-moe:3b" | "llama2" | "llama2:7b" | "llama2:13b" | "llama2:70b" | "llama3" | "llama3:8b" | "llama3:70b" | "llama3-chatqa" | "llama3-chatqa:8b" | "llama3-chatqa:70b" | "llama3-gradient" | "llama3-gradient:8b" | "llama3-gradient:70b" | "llama3.1" | "llama3.1:8b" | "llama3.1:70b" | "llama3.1:405b" | "llama3.2" | "llama3.2:1b" | "llama3.2:3b" | "llama3.2-vision" | "llama3.2-vision:11b" | "llama3.2-vision:90b" | "llama3.3" | "llama3.3:70b" | "llama4" | "llama4:16x17b" | "llama4:128x17b" | "llama-guard3" | "llama-guard3:1b" | "llama-guard3:8b" | "llava" | "llava:7b" | "llava:13b" | "llava:34b" | "llava-llama3" | "llava-llama3:8b" | "llava-phi3" | "llava-phi3:3.8b" | "marco-o1" | "marco-o1:7b" | "mistral" | "mistral:7b" | "mistral-large" | "mistral-large:123b" | "mistral-nemo" | "mistral-nemo:12b" | "mistral-small" | "mistral-small:22b" | "mixtral" | "mixtral:8x7b" | "mixtral:8x22b" | "moondream" | "moondream:1.8b" | "openhermes" | "openhermes:v2.5" | "nemotron" | "nemotron:70b" | "nemotron-mini" | "nemotron-mini:4b" | "olmo" | "olmo:7b" | "olmo:13b" | "opencoder" | "opencoder:1.5b" | "opencoder:8b" | "phi3" | "phi3:3.8b" | "phi3:14b" | "phi3.5" | "phi3.5:3.8b" | "phi4" | "phi4:14b" | "qwen" | "qwen:7b" | "qwen:14b" | "qwen:32b" | "qwen:72b" | "qwen:110b" | "qwen2" | "qwen2:0.5b" | "qwen2:1.5b" | "qwen2:7b" | "qwen2:72b" | "qwen2.5" | "qwen2.5:0.5b" | "qwen2.5:1.5b" | "qwen2.5:3b" | "qwen2.5:7b" | "qwen2.5:14b" | "qwen2.5:32b" | "qwen2.5:72b" | "qwen2.5-coder" | "qwen2.5-coder:0.5b" | "qwen2.5-coder:1.5b" | "qwen2.5-coder:3b" | "qwen2.5-coder:7b" | "qwen2.5-coder:14b" | "qwen2.5-coder:32b" | "qwen3" | "qwen3:0.6b" | "qwen3:1.7b" | "qwen3:4b" | "qwen3:8b" | "qwen3:14b" | "qwen3:30b" | "qwen3:32b" | "qwen3:235b" | "qwq" | "qwq:32b" | "sailor2" | "sailor2:1b" | "sailor2:8b" | "sailor2:20b" | "shieldgemma" | "shieldgemma:2b" | "shieldgemma:9b" | "shieldgemma:27b" | "smallthinker" | "smallthinker:3b" | "smollm" | "smollm:135m" | "smollm:360m" | "smollm:1.7b" | "tinyllama" | "tinyllama:1.1b" | "tulu3" | "tulu3:8b" | "tulu3:70b" | (string & {});
|
|
6
6
|
declare const ollamaProviderOptions: z.ZodObject<{
|
|
7
|
-
think: z.ZodOptional<z.
|
|
8
|
-
low: "low";
|
|
9
|
-
medium: "medium";
|
|
10
|
-
high: "high";
|
|
11
|
-
}>]>>;
|
|
7
|
+
think: z.ZodOptional<z.ZodBoolean>;
|
|
12
8
|
options: z.ZodOptional<z.ZodObject<{
|
|
13
9
|
num_ctx: z.ZodOptional<z.ZodNumber>;
|
|
14
10
|
repeat_last_n: z.ZodOptional<z.ZodNumber>;
|
|
@@ -31,12 +27,9 @@ interface OllamaCompletionSettings {
|
|
|
31
27
|
* the model's thinking from the model's output. When disabled, the model will not think
|
|
32
28
|
* and directly output the content.
|
|
33
29
|
*
|
|
34
|
-
*
|
|
35
|
-
* For other models: accepts boolean true/false.
|
|
36
|
-
*
|
|
37
|
-
* Only supported by certain models like DeepSeek R1, Qwen 3, and GPT-OSS.
|
|
30
|
+
* Only supported by certain models like DeepSeek R1 and Qwen 3.
|
|
38
31
|
*/
|
|
39
|
-
think?: boolean
|
|
32
|
+
think?: boolean;
|
|
40
33
|
/**
|
|
41
34
|
* Echo back the prompt in addition to the completion.
|
|
42
35
|
*/
|
|
@@ -153,11 +146,7 @@ declare const ollamaEmbeddingProviderOptions: z.ZodObject<{
|
|
|
153
146
|
type OllamaEmbeddingProviderOptions = z.infer<typeof ollamaEmbeddingProviderOptions>;
|
|
154
147
|
|
|
155
148
|
declare const ollamaCompletionProviderOptions: z.ZodObject<{
|
|
156
|
-
think: z.ZodOptional<z.
|
|
157
|
-
low: "low";
|
|
158
|
-
medium: "medium";
|
|
159
|
-
high: "high";
|
|
160
|
-
}>]>>;
|
|
149
|
+
think: z.ZodOptional<z.ZodBoolean>;
|
|
161
150
|
user: z.ZodOptional<z.ZodString>;
|
|
162
151
|
suffix: z.ZodOptional<z.ZodString>;
|
|
163
152
|
echo: z.ZodOptional<z.ZodBoolean>;
|
package/dist/index.d.ts
CHANGED
|
@@ -4,11 +4,7 @@ import { z } from 'zod/v4';
|
|
|
4
4
|
|
|
5
5
|
type OllamaChatModelId = "athene-v2" | "athene-v2:72b" | "aya-expanse" | "aya-expanse:8b" | "aya-expanse:32b" | "codegemma" | "codegemma:2b" | "codegemma:7b" | "codellama" | "codellama:7b" | "codellama:13b" | "codellama:34b" | "codellama:70b" | "codellama:code" | "codellama:python" | "command-r" | "command-r:35b" | "command-r-plus" | "command-r-plus:104b" | "command-r7b" | "command-r7b:7b" | "deepseek-r1" | "deepseek-r1:1.5b" | "deepseek-r1:7b" | "deepseek-r1:8b" | "deepseek-r1:14b" | "deepseek-r1:32b" | "deepseek-r1:70b" | "deepseek-r1:671b" | "deepseek-coder-v2" | "deepseek-coder-v2:16b" | "deepseek-coder-v2:236b" | "deepseek-v3" | "deepseek-v3:671b" | "devstral" | "devstral:24b" | "dolphin3" | "dolphin3:8b" | "exaone3.5" | "exaone3.5:2.4b" | "exaone3.5:7.8b" | "exaone3.5:32b" | "falcon2" | "falcon2:11b" | "falcon3" | "falcon3:1b" | "falcon3:3b" | "falcon3:7b" | "falcon3:10b" | "firefunction-v2" | "firefunction-v2:70b" | "gemma" | "gemma:2b" | "gemma:7b" | "gemma2" | "gemma2:2b" | "gemma2:9b" | "gemma2:27b" | "gemma3" | "gemma3:1b" | "gemma3:4b" | "gemma3:12b" | "gemma3:27b" | "granite3-dense" | "granite3-dense:2b" | "granite3-dense:8b" | "granite3-guardian" | "granite3-guardian:2b" | "granite3-guardian:8b" | "granite3-moe" | "granite3-moe:1b" | "granite3-moe:3b" | "granite3.1-dense" | "granite3.1-dense:2b" | "granite3.1-dense:8b" | "granite3.1-moe" | "granite3.1-moe:1b" | "granite3.1-moe:3b" | "llama2" | "llama2:7b" | "llama2:13b" | "llama2:70b" | "llama3" | "llama3:8b" | "llama3:70b" | "llama3-chatqa" | "llama3-chatqa:8b" | "llama3-chatqa:70b" | "llama3-gradient" | "llama3-gradient:8b" | "llama3-gradient:70b" | "llama3.1" | "llama3.1:8b" | "llama3.1:70b" | "llama3.1:405b" | "llama3.2" | "llama3.2:1b" | "llama3.2:3b" | "llama3.2-vision" | "llama3.2-vision:11b" | "llama3.2-vision:90b" | "llama3.3" | "llama3.3:70b" | "llama4" | "llama4:16x17b" | "llama4:128x17b" | "llama-guard3" | "llama-guard3:1b" | "llama-guard3:8b" | "llava" | "llava:7b" | "llava:13b" | "llava:34b" | "llava-llama3" | "llava-llama3:8b" | "llava-phi3" | "llava-phi3:3.8b" | "marco-o1" | "marco-o1:7b" | "mistral" | "mistral:7b" | "mistral-large" | "mistral-large:123b" | "mistral-nemo" | "mistral-nemo:12b" | "mistral-small" | "mistral-small:22b" | "mixtral" | "mixtral:8x7b" | "mixtral:8x22b" | "moondream" | "moondream:1.8b" | "openhermes" | "openhermes:v2.5" | "nemotron" | "nemotron:70b" | "nemotron-mini" | "nemotron-mini:4b" | "olmo" | "olmo:7b" | "olmo:13b" | "opencoder" | "opencoder:1.5b" | "opencoder:8b" | "phi3" | "phi3:3.8b" | "phi3:14b" | "phi3.5" | "phi3.5:3.8b" | "phi4" | "phi4:14b" | "qwen" | "qwen:7b" | "qwen:14b" | "qwen:32b" | "qwen:72b" | "qwen:110b" | "qwen2" | "qwen2:0.5b" | "qwen2:1.5b" | "qwen2:7b" | "qwen2:72b" | "qwen2.5" | "qwen2.5:0.5b" | "qwen2.5:1.5b" | "qwen2.5:3b" | "qwen2.5:7b" | "qwen2.5:14b" | "qwen2.5:32b" | "qwen2.5:72b" | "qwen2.5-coder" | "qwen2.5-coder:0.5b" | "qwen2.5-coder:1.5b" | "qwen2.5-coder:3b" | "qwen2.5-coder:7b" | "qwen2.5-coder:14b" | "qwen2.5-coder:32b" | "qwen3" | "qwen3:0.6b" | "qwen3:1.7b" | "qwen3:4b" | "qwen3:8b" | "qwen3:14b" | "qwen3:30b" | "qwen3:32b" | "qwen3:235b" | "qwq" | "qwq:32b" | "sailor2" | "sailor2:1b" | "sailor2:8b" | "sailor2:20b" | "shieldgemma" | "shieldgemma:2b" | "shieldgemma:9b" | "shieldgemma:27b" | "smallthinker" | "smallthinker:3b" | "smollm" | "smollm:135m" | "smollm:360m" | "smollm:1.7b" | "tinyllama" | "tinyllama:1.1b" | "tulu3" | "tulu3:8b" | "tulu3:70b" | (string & {});
|
|
6
6
|
declare const ollamaProviderOptions: z.ZodObject<{
|
|
7
|
-
think: z.ZodOptional<z.
|
|
8
|
-
low: "low";
|
|
9
|
-
medium: "medium";
|
|
10
|
-
high: "high";
|
|
11
|
-
}>]>>;
|
|
7
|
+
think: z.ZodOptional<z.ZodBoolean>;
|
|
12
8
|
options: z.ZodOptional<z.ZodObject<{
|
|
13
9
|
num_ctx: z.ZodOptional<z.ZodNumber>;
|
|
14
10
|
repeat_last_n: z.ZodOptional<z.ZodNumber>;
|
|
@@ -31,12 +27,9 @@ interface OllamaCompletionSettings {
|
|
|
31
27
|
* the model's thinking from the model's output. When disabled, the model will not think
|
|
32
28
|
* and directly output the content.
|
|
33
29
|
*
|
|
34
|
-
*
|
|
35
|
-
* For other models: accepts boolean true/false.
|
|
36
|
-
*
|
|
37
|
-
* Only supported by certain models like DeepSeek R1, Qwen 3, and GPT-OSS.
|
|
30
|
+
* Only supported by certain models like DeepSeek R1 and Qwen 3.
|
|
38
31
|
*/
|
|
39
|
-
think?: boolean
|
|
32
|
+
think?: boolean;
|
|
40
33
|
/**
|
|
41
34
|
* Echo back the prompt in addition to the completion.
|
|
42
35
|
*/
|
|
@@ -153,11 +146,7 @@ declare const ollamaEmbeddingProviderOptions: z.ZodObject<{
|
|
|
153
146
|
type OllamaEmbeddingProviderOptions = z.infer<typeof ollamaEmbeddingProviderOptions>;
|
|
154
147
|
|
|
155
148
|
declare const ollamaCompletionProviderOptions: z.ZodObject<{
|
|
156
|
-
think: z.ZodOptional<z.
|
|
157
|
-
low: "low";
|
|
158
|
-
medium: "medium";
|
|
159
|
-
high: "high";
|
|
160
|
-
}>]>>;
|
|
149
|
+
think: z.ZodOptional<z.ZodBoolean>;
|
|
161
150
|
user: z.ZodOptional<z.ZodString>;
|
|
162
151
|
suffix: z.ZodOptional<z.ZodString>;
|
|
163
152
|
echo: z.ZodOptional<z.ZodBoolean>;
|
package/dist/index.js
CHANGED
|
@@ -31,7 +31,7 @@ var import_provider_utils8 = require("@ai-sdk/provider-utils");
|
|
|
31
31
|
|
|
32
32
|
// src/completion/ollama-completion-language-model.ts
|
|
33
33
|
var import_provider_utils2 = require("@ai-sdk/provider-utils");
|
|
34
|
-
var
|
|
34
|
+
var import_v42 = require("zod/v4");
|
|
35
35
|
|
|
36
36
|
// src/completion/ollama-error.ts
|
|
37
37
|
var import_v4 = require("zod/v4");
|
|
@@ -156,63 +156,38 @@ function getResponseMetadata({
|
|
|
156
156
|
};
|
|
157
157
|
}
|
|
158
158
|
|
|
159
|
-
// src/ollama-
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
* the model's thinking from the model's output. When disabled, the model will not think
|
|
165
|
-
* and directly output the content.
|
|
166
|
-
*
|
|
167
|
-
* For GPT-OSS models: accepts "low", "medium", or "high" to tune trace length.
|
|
168
|
-
* For other models: accepts boolean true/false.
|
|
169
|
-
*
|
|
170
|
-
* Only supported by certain models like DeepSeek R1, Qwen 3, and GPT-OSS.
|
|
171
|
-
*/
|
|
172
|
-
think: import_v42.z.union([
|
|
173
|
-
import_v42.z.boolean(),
|
|
174
|
-
import_v42.z.enum(["low", "medium", "high"])
|
|
175
|
-
]).optional(),
|
|
176
|
-
options: import_v42.z.object({
|
|
177
|
-
num_ctx: import_v42.z.number().optional(),
|
|
178
|
-
repeat_last_n: import_v42.z.number().optional(),
|
|
179
|
-
repeat_penalty: import_v42.z.number().optional(),
|
|
180
|
-
temperature: import_v42.z.number().optional(),
|
|
181
|
-
seed: import_v42.z.number().optional(),
|
|
182
|
-
stop: import_v42.z.array(import_v42.z.string()).optional(),
|
|
183
|
-
num_predict: import_v42.z.number().optional(),
|
|
184
|
-
top_k: import_v42.z.number().optional(),
|
|
185
|
-
top_p: import_v42.z.number().optional(),
|
|
186
|
-
min_p: import_v42.z.number().optional()
|
|
187
|
-
}).optional()
|
|
188
|
-
});
|
|
189
|
-
function validateThinkParameter(modelId, think) {
|
|
190
|
-
if (think === void 0) {
|
|
191
|
-
return void 0;
|
|
192
|
-
}
|
|
193
|
-
const isGptOss = modelId.toLowerCase().includes("gpt-oss");
|
|
194
|
-
if (isGptOss) {
|
|
195
|
-
if (typeof think === "boolean") {
|
|
196
|
-
return think ? "medium" : void 0;
|
|
197
|
-
}
|
|
198
|
-
return think;
|
|
199
|
-
} else {
|
|
200
|
-
if (typeof think === "string") {
|
|
201
|
-
return think !== void 0;
|
|
159
|
+
// src/completion/ollama-completion-language-model.ts
|
|
160
|
+
function createJsonStreamResponseHandler(schema) {
|
|
161
|
+
return async ({ response }) => {
|
|
162
|
+
if (!response.body) {
|
|
163
|
+
throw new Error("Response body is null");
|
|
202
164
|
}
|
|
203
|
-
|
|
204
|
-
|
|
165
|
+
const stream = response.body.pipeThrough(new TextDecoderStream()).pipeThrough(new TransformStream({
|
|
166
|
+
transform(chunk, controller) {
|
|
167
|
+
const lines = chunk.split("\n");
|
|
168
|
+
for (const line of lines) {
|
|
169
|
+
if (line.trim()) {
|
|
170
|
+
const result = (0, import_provider_utils2.safeParseJSON)({ text: line.trim(), schema });
|
|
171
|
+
controller.enqueue(result);
|
|
172
|
+
}
|
|
173
|
+
}
|
|
174
|
+
}
|
|
175
|
+
}));
|
|
176
|
+
const responseHeaders = {};
|
|
177
|
+
response.headers.forEach((value, key) => {
|
|
178
|
+
responseHeaders[key] = value;
|
|
179
|
+
});
|
|
180
|
+
return {
|
|
181
|
+
value: stream,
|
|
182
|
+
responseHeaders
|
|
183
|
+
};
|
|
184
|
+
};
|
|
205
185
|
}
|
|
206
|
-
|
|
207
|
-
|
|
208
|
-
|
|
209
|
-
|
|
210
|
-
|
|
211
|
-
import_v43.z.enum(["low", "medium", "high"])
|
|
212
|
-
]).optional(),
|
|
213
|
-
user: import_v43.z.string().optional(),
|
|
214
|
-
suffix: import_v43.z.string().optional(),
|
|
215
|
-
echo: import_v43.z.boolean().optional()
|
|
186
|
+
var ollamaCompletionProviderOptions = import_v42.z.object({
|
|
187
|
+
think: import_v42.z.boolean().optional(),
|
|
188
|
+
user: import_v42.z.string().optional(),
|
|
189
|
+
suffix: import_v42.z.string().optional(),
|
|
190
|
+
echo: import_v42.z.boolean().optional()
|
|
216
191
|
});
|
|
217
192
|
var OllamaCompletionLanguageModel = class {
|
|
218
193
|
constructor(modelId, settings, config) {
|
|
@@ -270,14 +245,13 @@ var OllamaCompletionLanguageModel = class {
|
|
|
270
245
|
}
|
|
271
246
|
const { prompt: completionPrompt, stopSequences } = convertToOllamaCompletionPrompt({ prompt });
|
|
272
247
|
const stop = [...stopSequences != null ? stopSequences : [], ...userStopSequences != null ? userStopSequences : []];
|
|
273
|
-
const validatedThink = validateThinkParameter(this.modelId, ollamaOptions.think);
|
|
274
248
|
return {
|
|
275
249
|
args: {
|
|
276
250
|
// model id:
|
|
277
251
|
model: this.modelId,
|
|
278
252
|
// Ollama-supported settings:
|
|
279
253
|
user: ollamaOptions.user,
|
|
280
|
-
think:
|
|
254
|
+
think: ollamaOptions.think,
|
|
281
255
|
// standardized settings:
|
|
282
256
|
max_tokens: maxOutputTokens,
|
|
283
257
|
temperature,
|
|
@@ -356,7 +330,7 @@ var OllamaCompletionLanguageModel = class {
|
|
|
356
330
|
headers: (0, import_provider_utils2.combineHeaders)(this.config.headers(), options.headers),
|
|
357
331
|
body,
|
|
358
332
|
failedResponseHandler: ollamaFailedResponseHandler,
|
|
359
|
-
successfulResponseHandler:
|
|
333
|
+
successfulResponseHandler: createJsonStreamResponseHandler(
|
|
360
334
|
baseOllamaResponseSchema
|
|
361
335
|
),
|
|
362
336
|
abortSignal: options.abortSignal,
|
|
@@ -417,28 +391,28 @@ var OllamaCompletionLanguageModel = class {
|
|
|
417
391
|
};
|
|
418
392
|
}
|
|
419
393
|
};
|
|
420
|
-
var baseOllamaResponseSchema =
|
|
421
|
-
model:
|
|
422
|
-
created_at:
|
|
423
|
-
response:
|
|
424
|
-
done:
|
|
425
|
-
context:
|
|
426
|
-
eval_count:
|
|
427
|
-
eval_duration:
|
|
428
|
-
load_duration:
|
|
429
|
-
total_duration:
|
|
430
|
-
prompt_eval_count:
|
|
431
|
-
prompt_eval_duration:
|
|
394
|
+
var baseOllamaResponseSchema = import_v42.z.object({
|
|
395
|
+
model: import_v42.z.string(),
|
|
396
|
+
created_at: import_v42.z.string(),
|
|
397
|
+
response: import_v42.z.string(),
|
|
398
|
+
done: import_v42.z.boolean(),
|
|
399
|
+
context: import_v42.z.array(import_v42.z.number()),
|
|
400
|
+
eval_count: import_v42.z.number().optional(),
|
|
401
|
+
eval_duration: import_v42.z.number().optional(),
|
|
402
|
+
load_duration: import_v42.z.number().optional(),
|
|
403
|
+
total_duration: import_v42.z.number().optional(),
|
|
404
|
+
prompt_eval_count: import_v42.z.number().optional(),
|
|
405
|
+
prompt_eval_duration: import_v42.z.number().optional()
|
|
432
406
|
});
|
|
433
407
|
|
|
434
408
|
// src/embedding/ollama-embedding-model.ts
|
|
435
409
|
var import_provider2 = require("@ai-sdk/provider");
|
|
436
410
|
var import_provider_utils3 = require("@ai-sdk/provider-utils");
|
|
437
|
-
var
|
|
438
|
-
var ollamaEmbeddingProviderOptions =
|
|
439
|
-
dimensions:
|
|
440
|
-
truncate:
|
|
441
|
-
keepAlive:
|
|
411
|
+
var import_v43 = require("zod/v4");
|
|
412
|
+
var ollamaEmbeddingProviderOptions = import_v43.z.object({
|
|
413
|
+
dimensions: import_v43.z.number().optional(),
|
|
414
|
+
truncate: import_v43.z.boolean().optional(),
|
|
415
|
+
keepAlive: import_v43.z.string().optional()
|
|
442
416
|
});
|
|
443
417
|
var OllamaEmbeddingModel = class {
|
|
444
418
|
constructor(modelId, settings, config) {
|
|
@@ -520,12 +494,12 @@ var OllamaEmbeddingModel = class {
|
|
|
520
494
|
};
|
|
521
495
|
}
|
|
522
496
|
};
|
|
523
|
-
var ollamaTextEmbeddingResponseSchema =
|
|
524
|
-
model:
|
|
525
|
-
embeddings:
|
|
526
|
-
total_duration:
|
|
527
|
-
load_duration:
|
|
528
|
-
prompt_eval_count:
|
|
497
|
+
var ollamaTextEmbeddingResponseSchema = import_v43.z.object({
|
|
498
|
+
model: import_v43.z.string(),
|
|
499
|
+
embeddings: import_v43.z.array(import_v43.z.array(import_v43.z.number())),
|
|
500
|
+
total_duration: import_v43.z.number(),
|
|
501
|
+
load_duration: import_v43.z.number(),
|
|
502
|
+
prompt_eval_count: import_v43.z.number()
|
|
529
503
|
});
|
|
530
504
|
|
|
531
505
|
// src/responses/ollama-responses-language-model.ts
|
|
@@ -857,6 +831,31 @@ function prepareResponsesTools({
|
|
|
857
831
|
}
|
|
858
832
|
}
|
|
859
833
|
|
|
834
|
+
// src/ollama-chat-settings.ts
|
|
835
|
+
var import_v44 = require("zod/v4");
|
|
836
|
+
var ollamaProviderOptions = import_v44.z.object({
|
|
837
|
+
/**
|
|
838
|
+
* Enable or disable the model's thinking process. When enabled, the output will separate
|
|
839
|
+
* the model's thinking from the model's output. When disabled, the model will not think
|
|
840
|
+
* and directly output the content.
|
|
841
|
+
*
|
|
842
|
+
* Only supported by certain models like DeepSeek R1 and Qwen 3.
|
|
843
|
+
*/
|
|
844
|
+
think: import_v44.z.boolean().optional(),
|
|
845
|
+
options: import_v44.z.object({
|
|
846
|
+
num_ctx: import_v44.z.number().optional(),
|
|
847
|
+
repeat_last_n: import_v44.z.number().optional(),
|
|
848
|
+
repeat_penalty: import_v44.z.number().optional(),
|
|
849
|
+
temperature: import_v44.z.number().optional(),
|
|
850
|
+
seed: import_v44.z.number().optional(),
|
|
851
|
+
stop: import_v44.z.array(import_v44.z.string()).optional(),
|
|
852
|
+
num_predict: import_v44.z.number().optional(),
|
|
853
|
+
top_k: import_v44.z.number().optional(),
|
|
854
|
+
top_p: import_v44.z.number().optional(),
|
|
855
|
+
min_p: import_v44.z.number().optional()
|
|
856
|
+
}).optional()
|
|
857
|
+
});
|
|
858
|
+
|
|
860
859
|
// src/responses/ollama-responses-request-builder.ts
|
|
861
860
|
var OllamaRequestBuilder = class {
|
|
862
861
|
async buildRequest({
|
|
@@ -949,8 +948,7 @@ var OllamaRequestBuilder = class {
|
|
|
949
948
|
responseFormat,
|
|
950
949
|
ollamaOptions
|
|
951
950
|
}) {
|
|
952
|
-
var _a;
|
|
953
|
-
const validatedThink = validateThinkParameter(modelId, ollamaOptions == null ? void 0 : ollamaOptions.think);
|
|
951
|
+
var _a, _b;
|
|
954
952
|
return {
|
|
955
953
|
model: modelId,
|
|
956
954
|
messages: convertToOllamaChatMessages({
|
|
@@ -963,8 +961,8 @@ var OllamaRequestBuilder = class {
|
|
|
963
961
|
...(responseFormat == null ? void 0 : responseFormat.type) === "json" && {
|
|
964
962
|
format: responseFormat.schema != null ? responseFormat.schema : "json"
|
|
965
963
|
},
|
|
966
|
-
think:
|
|
967
|
-
options: (
|
|
964
|
+
think: (_a = ollamaOptions == null ? void 0 : ollamaOptions.think) != null ? _a : false,
|
|
965
|
+
options: (_b = ollamaOptions == null ? void 0 : ollamaOptions.options) != null ? _b : void 0
|
|
968
966
|
};
|
|
969
967
|
}
|
|
970
968
|
};
|
|
@@ -1264,6 +1262,32 @@ var OllamaStreamProcessor = class {
|
|
|
1264
1262
|
};
|
|
1265
1263
|
|
|
1266
1264
|
// src/responses/ollama-responses-language-model.ts
|
|
1265
|
+
function createJsonStreamResponseHandler2(schema) {
|
|
1266
|
+
return async ({ response }) => {
|
|
1267
|
+
if (!response.body) {
|
|
1268
|
+
throw new Error("Response body is null");
|
|
1269
|
+
}
|
|
1270
|
+
const stream = response.body.pipeThrough(new TextDecoderStream()).pipeThrough(new TransformStream({
|
|
1271
|
+
transform(chunk, controller) {
|
|
1272
|
+
const lines = chunk.split("\n");
|
|
1273
|
+
for (const line of lines) {
|
|
1274
|
+
if (line.trim()) {
|
|
1275
|
+
const result = (0, import_provider_utils7.safeParseJSON)({ text: line.trim(), schema });
|
|
1276
|
+
controller.enqueue(result);
|
|
1277
|
+
}
|
|
1278
|
+
}
|
|
1279
|
+
}
|
|
1280
|
+
}));
|
|
1281
|
+
const responseHeaders = {};
|
|
1282
|
+
response.headers.forEach((value, key) => {
|
|
1283
|
+
responseHeaders[key] = value;
|
|
1284
|
+
});
|
|
1285
|
+
return {
|
|
1286
|
+
value: stream,
|
|
1287
|
+
responseHeaders
|
|
1288
|
+
};
|
|
1289
|
+
};
|
|
1290
|
+
}
|
|
1267
1291
|
var OllamaResponsesLanguageModel = class {
|
|
1268
1292
|
constructor(modelId, config) {
|
|
1269
1293
|
this.specificationVersion = "v2";
|
|
@@ -1321,7 +1345,7 @@ var OllamaResponsesLanguageModel = class {
|
|
|
1321
1345
|
headers: (0, import_provider_utils7.combineHeaders)(this.config.headers(), options.headers),
|
|
1322
1346
|
body: { ...body, stream: true },
|
|
1323
1347
|
failedResponseHandler: ollamaFailedResponseHandler,
|
|
1324
|
-
successfulResponseHandler: (
|
|
1348
|
+
successfulResponseHandler: createJsonStreamResponseHandler2(baseOllamaResponseSchema2),
|
|
1325
1349
|
abortSignal: options.abortSignal,
|
|
1326
1350
|
fetch: this.config.fetch
|
|
1327
1351
|
});
|