本文将Ollama官方支持的每个 HTTP API 的用法、参数和场景都整理出来并全部调用了一遍,顺便把 generate 和 chat 到底是什么关系和区别、什么时候用哪个。
Ollama HTTP API 基本约定
默认的 API 地址是 http://localhost:11434/api,全部请求都是用 JSON body、统一用 POST(除了个别 GET 方法),所有响应都支持流式和非流式两种模式,通过 "stream": false 来关掉流式开关。
先大致感受一下,最基础的请求长这样:
curl http://localhost:11434/api/generate -d '{
"model": "qwen3.5:9b",
"prompt": "介绍一下你自己",
"stream": false
}'
Ollama API 中的 generate vs chat:核心区别和选择逻辑
很多人一开始困惑这两个端点到底有什么区别。用表格说清楚:
| 维度 | /api/generate | /api/chat |
|---|---|---|
| 输入格式 | prompt 字符串 |
messages 数组(每条消息有 role) |
| 上下文管理 | 依赖 suffix 或手动传 context |
messages 自动维护历史,支持 system/user/assistant/tool 四种角色 |
| 适用场景 | 单次补全、填充中间内容(FIM)、base model 直接调用 | 多轮对话、有上下文依赖的任务、instruction-tuned model |
| 技术定位 | 更接近模型原生推理接口 | 更高层次、为聊天场景设计的封装 |
| 额外能力 | 支持 suffix 参数(用于代码补全场景) |
支持 tools 参数(工具调用) |
generate 像一个裸函数——你给它一句“继续写下去”,它返回续写的结果;chat 像一个有记忆的对话系统——你给它几轮对话记录(包括用户说了什么、助手回了什么),它推理出下一轮的回复。chat 内部其实就是把 messages 数组按某种模板转成模型能理解的 prompt 再调用 generate 的逻辑,但帮你省掉了手动管理模版的心智负担。
用 generate 复现多轮对话确实也能做到:需要每次请求里把历史对话手动压缩成上下文,丢进 context 字段传回去,维护成本极高。一般不推荐这么干,除非你有特殊理由(比如对接的是某个只暴露了 /generate 接口的老系统)。绝大多数情况下,只要你的使用场景是一次问答以上的循环,就用 chat。
generate 底层的裸推理更适合单轮复杂控制(FIM 代码填充、结构化输出精度优先场景),chat 里的 messages + tools 组合拳大幅简化多轮对话和外部函数调用链的开发成本。刚接触 Ollama 的话建议从 /api/chat 开始,遇到代码补全或更复杂的 prompt 控制再切回 /api/generate。
Ollama 所有 API 端点详解
下面挨个过一遍官方支持的每个端点,用 qwen3.5:9b 做示例。
1. POST /api/generate —— 补全推理
生成给定 prompt 的模型回复。支持流式和非流式两种模式。
完整参数列表(入参 body JSON 字段):
| 参数 | 类型 | 必填 | 说明 |
|---|---|---|---|
model |
string | 是 | 模型名称,比如 qwen3.5:9b |
prompt |
string | 是 | 文本 prompt |
suffix |
string | 否 | 代码补全场景的补全后缀,模型会尝试填充 prompt 和 suffix 之间的内容 |
images |
string[] | 否 | 图片 base64 编码数组(视觉模型用比如 llava、qwen3-vl) |
think |
bool/string | 否 | true/false/high/medium/low,控制推理模型的思考模式 |
format |
string/object | 否 | "json" 强制输出 JSON,或一个 JSON Schema 对象启用结构化输出 |
options |
object | 否 | 运行时参数,可以覆盖温度、top_p、seed 等(见下面说明) |
system |
string | 否 | 系统提示词,临时覆盖 Modelfile 里的定义 |
template |
string | 否 | 提示模板,临时覆盖 Modelfile |
stream |
bool | 否 | false 关闭流式响应(默认 true) |
raw |
bool | 否 | true 则跳过模板渲染,直接把 prompt 原样传给模型 |
keep_alive |
string/int | 否 | 模型在内存中保留时长,如 "10m" 或 0(立即卸载) |
context (已弃用) |
int[] | 否 | 对话上下文编码,用于手动延续上一轮对话 |
Response 返回一个流(streaming)或单个 JSON 对象。字段包括:
| 字段 | 说明 |
|---|---|
model |
使用的模型名称 |
created_at |
响应创建时间(ISO 8601 格式) |
response |
生成的文本内容 |
thinking |
思考模式的推理输出(适用于 DeepSeek-R1/QwQ 等 thinking 模型) |
done |
是否完成(true/false) |
done_reason |
完成原因(stop/length 等) |
total_duration |
总耗时(纳秒) |
load_duration |
模型加载耗时(纳秒) |
prompt_eval_count |
输入 token 数量 |
prompt_eval_duration |
输入处理耗时(纳秒) |
eval_count |
输出 token 数量 |
eval_duration |
输出生成耗时(纳秒) |
logprobs |
输出 token 的 log 概率(logprobs 开启时返回) |
计算生成速度公式:eval_count / eval_duration * 10^9(token/s)。
示例 1:单次补全(非流式)
curl http://localhost:11434/api/generate -d '{
"model": "qwen3.5:9b",
"prompt": "用一句话解释什么是递归",
"stream": false
}'
Response 示例:
{
"model": "qwen3.5:9b",
"created_at": "2025-01-15T10:30:00Z",
"response": "递归就是函数调用自身来解决问题的编程技巧。",
"done": true,
"total_duration": 2850000000,
"load_duration": 150000000,
"prompt_eval_count": 12,
"prompt_eval_duration": 50000000,
"eval_count": 45,
"eval_duration": 2650000000
}
示例 2:代码补全场景(prompt + suffix)
generate 独有的 suffix 参数常用于代码自动补全(Fill-in-the-middle)。比如你想让模型生成函数体中间部分的代码:
curl http://localhost:11434/api/generate -d '{
"model": "qwen3.5:9b",
"prompt": "def quick_sort(arr):\n if len(arr) <= 1:",
"suffix": "\n return arr",
"options": {"temperature": 0},
"stream": false
}'
普通的 generate 只能给你「往后续写」,你给 prompt 它就从 prompt 末尾接着生成,没法在中间插一段再回到结尾。suffix 的作用就是设定一个「结尾锚点」,模型会努力生成一段能顺接上这个结尾的内容。
示例 3:开启思考模式(think 参数)
如果模型本身支持推理能力(比如 deepseek-r1、qwen3-thinking 系列),加上 think 参数可以看到模型的推理链条:
curl http://localhost:11434/api/generate -d '{
"model": "qwen3.5:9b",
"prompt": "四则运算里,先乘除后加减的道理是什么?",
"think": "high",
"stream": false
}'
关联 think 参数支持三种级别:
true/false:布尔开关high:强推理,质量最高但耗时最长medium/low:折衷模式
示例 4:结构化输出 JSON(JSON Schema)
curl http://localhost:11434/api/generate -d '{
"model": "qwen3.5:9b",
"prompt": "介绍一下法国。使用 JSON 格式输出。",
"format": {
"type": "object",
"properties": {
"name": {"type": "string"},
"capital": {"type": "string"},
"population": {"type": "number"}
},
"required": ["name", "capital"]
},
"stream": false
}'
响应里 response 字段会返回符合 JSON Schema 的字符串,使用时需要 JSON.parse 解析。
关于结构化输出还有一个细节:Ollama 官方在 Cloud 版里暂时不支持这个功能,必须跑本地模型才生效。另一个值得注意的点是:即便给了 Schema,你仍然需要在 prompt 中用文字明确提醒模型“输出 JSON 格式”,否则模型容易输出大量无意义的空白或自然语言。调优推荐 options 里设 temperature: 0,确定性更强。
示例 5:多模态图片识别
请求里直接塞 base64 编码的图片:
curl http://localhost:11434/api/generate -d '{
"model": "qwen3.5:9b",
"prompt": "这张图片里有什么?",
"images": ["iVBORw0KGgoAAAANS...base64..."],
"stream": false
}'
示例 6:控制模型行为(options 详细参数一览)
options 字段可以覆盖 Modelfile 里的参数。常用参数如下(列了几个最常用的):
| 参数 | 类型 | 默认说明 |
|---|---|---|
temperature |
float | 控制随机性,越高越随机。推荐 0.1–1.0 |
top_p |
float | 核采样的阈值,0.9 较保守,1.0 全采样 |
seed |
int | 随机种子,固定后输出可重现 |
num_predict |
int | 最大输出 token 数 |
num_ctx |
int | 上下文 token 数(越大吃显存越多) |
repeat_penalty |
float | 重复惩罚,有利于减少循环重复 |
stop |
string[] | 停止词数组 |
实际使用时的写法:
curl http://localhost:11434/api/generate -d '{
"model": "qwen3.5:9b",
"prompt": "写出三个有趣的编程笑话",
"options": {
"temperature": 0.8,
"top_p": 0.9,
"seed": 42,
"num_predict": 256,
"num_ctx": 4096,
"repeat_penalty": 1.1,
"stop": ["\n\n", "。"],
"num_gpu": 1
},
"stream": false
}'
示例 7:控制模型驻留时间(keep_alive)
默认模型响应后会在内存里保留 5 分钟(5m),方便下次调用无需重加载:
- 设成
"0"立即卸载(请求结束后立刻释放显存/内存) - 设成
"-1"永久保持加载(直到进程重启或手动停止) - 推荐开发测试用
keep_alive: 0,省资源
2. POST /api/chat —— 对话补全
聊天场景的最优解。把消息历史放在 messages 数组里,数组里每条消息必须带 role 和 content 两个字段。
参数列表(入参 body JSON 字段):
| 参数 | 类型 | 必填 | 说明 |
|---|---|---|---|
model |
string | 是 | 模型名称 |
messages |
array | 是 | 消息历史,每个对象包含 role 和 content |
tools |
array | 否 | 函数调用(工具调用)定义对象列表 |
format |
string/object | 否 | "json" 或 JSON Schema 对象 |
options |
object | 否 | 运行时参数(与 generate 的 options 相同) |
stream |
bool | 否 | 默认 true,设 false 关闭流式 |
keep_alive |
string/int | 否 | 模型驻留时间 |
logprobs |
bool | 否 | 是否返回 token 概率 |
top_logprobs |
int | 否 | 每个 token 位置返回多少候选 tokens |
Response 返回流或单个 JSON,核心字段为:
| 字段 | 说明 |
|---|---|
message |
包含 role, content, thinking, tool_calls 的子对象 |
message 的子结构里,thinking 存储推理过程(thinking 模式开启时),tool_calls 存储模型请求调用的函数。
示例 1:简单对话(非流式)
curl http://localhost:11434/api/chat -d '{
"model": "qwen3.5:9b",
"messages": [
{"role": "user", "content": "大模型幻觉是什么意思?"}
],
"stream": false
}'
示例 2:多轮对话(消息历史自动维护)
持续对话时,把之前 model 返回的老消息也传回去:
curl http://localhost:11434/api/chat -d '{
"model": "qwen3.5:9b",
"messages": [
{"role": "user", "content": "中国首都是哪里?"},
{"role": "assistant", "content": "北京。"},
{"role": "user", "content": "那边有什么著名景点?"}
],
"stream": false
}'
示例 3:工具调用(tools 参数详解)
chat 独有的 tools 能力,让模型不仅能回答,还能主动请求调用外部函数。workflow 通常是三步:
- 前端定义
tools(JSON schema 格式) - Model 返回
tool_calls(包含函数名和参数) - 前端执行函数,把结果用
tool角色的消息传回模型,模型再生成最终回答
工具定义示例:
curl http://localhost:11434/api/chat -d '{
"model": "qwen3.5:9b",
"messages": [
{"role": "user", "content": "东京现在的天气怎么样?"}
],
"tools": [
{
"type": "function",
"function": {
"name": "get_current_weather",
"description": "获取某个地点的当前天气",
"parameters": {
"type": "object",
"properties": {
"location": {"type": "string", "description": "城市名称"},
"unit": {"type": "string", "enum": ["celsius", "fahrenheit"]}
},
"required": ["location"]
}
}
}
],
"stream": false
}'
模型如果觉得需要调工具,响应里 message.tool_calls 会包含函数调用请求(如 {"name": "get_current_weather", "arguments": {"location": "Tokyo"}})。之后前端执行函数,将结果用 role: tool 消息发回,模型结合结果给出最终回复。
示例 4:结构化输出 + 低温度配置
和 generate 一致。把 Schema 放进 format:
curl -X POST http://localhost:11434/api/chat \
-H "Content-Type: application/json" \
-d '{
"model": "qwen3.5:9b",
"messages": [{"role": "user", "content": "写一个 json 描述巴黎"}],
"format": {
"type": "object",
"properties": {
"name": {"type": "string"},
"capital": {"type": "string"},
"languages": {"type": "array", "items": {"type": "string"}}
}
},
"options": {"temperature": 0},
"stream": false
}'
建议在 prompt 里也显式说明“以 JSON 格式输出”,双重加持下稳定性更高。
3. POST /api/create —— 创建模型
从一个现有模型派生新模型,或者从 safetensors/GGUF 文件构建模型。
Body 字段:model(新模型名)、from(源模型名)、system(系统提示)、template、quantize(量化等级 q4_K_M / q8_0)、stream(是否流式返回进度)。
示例:从 qwen3.5:9b 派生一个只说话委婉的新模型
curl http://localhost:11434/api/create -d '{
"model": "qwen3.5-polite",
"from": "qwen3.5:9b",
"system": "你是一个温和有礼的助手,说话要委婉、不要说出伤人的话"
}'
响应会返回一系列进度 status 更新(包括层写入、manifest 写入等)。最终状态 "status": "success" 表示完成。
4. GET /api/tags —— 列出本地已存在模型
curl http://localhost:11434/api/tags
返回已下载的所有模型列表,每个模型包含 name、size、quantization_level、parameter_size 等信息。
5. POST /api/show —— 查看模型详情
查看模型的详细信息(Modelfile、参数列表、系统提示词等)。
示例:
curl http://localhost:11434/api/show -d '{
"model": "qwen3.5:9b"
}'
输出包括 modelfile(实际生成该模型的 Modelfile 内容)、parameters(模型参数列表)、template(对话模板)、details(架构信息)和 capabilities(模型支持的能力)。verbose: true 可以查看更细的 tokenizer 映射。
6. POST /api/copy —— 复制模型
curl http://localhost:11434/api/copy -d '{
"source": "qwen3.5:9b",
"destination": "qwen3.5:9b-backup"
}'
成功后 200 OK,可做备份或实验不同参数配置时保留原模型。
7. DELETE /api/delete —— 删除模型
curl -X DELETE http://localhost:11434/api/delete -d '{
"model": "qwen3.5:9b-backup"
}'
响应 200 表示成功。
8. POST /api/pull —— 拉取模型(下载)
curl http://localhost:11434/api/pull -d '{
"model": "qwen3.5:9b"
}'
若 stream: true(默认)会流式返回 pulling manifest、digest 下载进度(含 total 和 completed)、verifying sha256、writing manifest 等。最终返回 {"status": "success"}。
9. POST /api/push —— 推送模型(上传仓库)
需要先登录 Ollama 账号(ollama signin)。命名格式要求 namespace/model:tag。
curl http://localhost:11434/api/push -d '{
"model": "my-username/qwen3.5:9b"
}'
返回流式上传状态,digest 级别显示总字节和已完成字节,最终返回 success。
10. POST /api/embed —— 生成向量嵌入
RAG(检索增强生成)场景的标配。把文本转成 vector embeddings。
支持单个输入或多个输入(输入列表)。
示例:单个文本
curl http://localhost:11434/api/embed -d '{
"model": "qwen3.5:9b",
"input": "递归是一种重要的编程思想"
}'
返回的 embeddings 数组包含一个 n 维向量数组(浮点数)。其中还能拿到 total_duration、load_duration 和 prompt_eval_count。
同时嵌入多个文本
curl http://localhost:11434/api/embed -d '{
"model": "qwen3.5:9b",
"input": ["文本A的语义", "文本B的语义", "文本C的语义"]
}'
truncate 参数默认为 true:超出上下文长度自动截断尾部;若设 "truncate": false 且输入超长则直接报错。dimensions 参数可以要求将输出向量降维到指定维数,适合特定向量数据库索引需求。
11. GET /api/ps —— 查看当前加载到内存里的模型
curl http://localhost:11434/api/ps
返回列表包括 name、size_vram(占用显存量)、expires_at(卸载时间)。
12. GET /api/version —— 查看 Ollama 版本
curl http://localhost:11434/api/version
返回 JSON:{"version": "0.5.x"}。
13. HEAD /api/blobs/:digest (检查 Blob 是否存在)
主要用于创建模型的底层验证。用来检查某个文件块的 SHA256 哈希是否已上传到服务器(注意是 Ollama 服务器本地硬盘,不是云端 registry)。
curl -I http://localhost:11434/api/blobs/sha256:29fdb92e57...
返回 200 说明 blob 存在,404 不存在。
14. POST /api/blobs/:digest (推送 Blob)
创建模型前推送 GGUF 或 safetensors 文件到本地缓存:
curl -T model.gguf -X POST http://localhost:11434/api/blobs/sha256:29fdb92e...
推送成功后在后来的 api/create 里可直接引用该 digest。
15. POST /api/generate(图像生成扩展模式,实验性)
视觉模型(如 flux 或 SD 变体)可以用相同的 generate 接口生成图片:
curl http://localhost:11434/api/generate -d '{
"model": "flux-schnell",
"prompt": "a sunset over mountains",
"width": 1024,
"height": 768
}'
响应里返回 image 字段(base64 编码的图片数据)和 done 标志。
