搭建你的第一座“模型工厂”——5分钟部署开源大模型
用Ollama部署开源模型,整个过程不超过5分钟。但跑起来只是第一步——这篇还会带你做一件事:在同一台机器上部署两个不同尺寸的模型,跑同一组问题,填一份模型选型对比表。以后你做技术选型时,这一套方法直接复用。
3.1 安装Ollama
Ollama是目前对开发者最友好的本地模型管理工具,一条命令就能拉取和运行模型。它提供类似Docker的使用体验,但没有容器那一层复杂度。
macOS / Windows
直接去 ollama.com 下载安装包,双击安装。装完后菜单栏会出现一个羊驼图标,后台服务自动启动。
Linux
bash
curl -fsSL https://ollama.com/install.sh | sh
装完验证一下:
bash
ollama --version
# 输出类似:ollama version 0.5.7
3.2 拉取并运行第一个模型
我们选用阿里开源的 Qwen2.5 系列,中文问答能力在开源模型里属于第一梯队。先拉7B版本:
bash
ollama pull qwen2.5:7b
7b 表示70亿参数,压缩后约4~5GB,8GB内存的机器能跑但会占满,16GB内存比较从容。
拉完后直接对话:
bash
ollama run qwen2.5:7b
你会进入一个交互式终端,直接打字提问:
text
>>> 用一句话解释Java的GC机制
模型会逐字输出回答。退出按 Ctrl + D 或输入 /bye。
如果下载速度慢,可以使用镜像加速。Ollama默认从它的官方仓库拉取,国内用户可设置环境变量:
bash
# 一些社区提供的加速镜像,按需选用
export OLLAMA_HOST=0.0.0.0:11434
3.3 用代码调用Ollama
终端里聊只能测试,真正开发要通过API。Ollama启动后默认监听 http://localhost:11434,接口兼容OpenAI格式,可以直接用我们第2篇写的 chat_completion_stream 来调。
但既然Ollama有自己的轻量API,这里给出一个更直接的封装,方便后续调用。
python
"""
ollama_client.py
Ollama模型的Python客户端封装
本文件对应 stage01_env/ollama_client.py
"""
import httpx
import json
from typing import AsyncIterator, Optional
class OllamaClient:
"""封装Ollama的聊天和生成接口。"""
def __init__(self, base_url: str = "http://localhost:11434"):
self.base_url = base_url.rstrip("/")
# ---------- 同步版 ----------
def chat_sync(self, model: str, messages: list[dict]) -> str:
"""
同步对话,返回完整回答。
用于脚本、测试、不需要流式的场景。
"""
url = f"{self.base_url}/api/chat"
payload = {
"model": model,
"messages": messages,
"stream": False,
}
with httpx.Client(timeout=120.0) as client:
response = client.post(url, json=payload)
response.raise_for_status()
data = response.json()
return data["message"]["content"]
# ---------- 异步流式版 ----------
async def chat_stream(self, model: str,
messages: list[dict]) -> AsyncIterator[str]:
"""
异步流式对话,逐token返回。
适用于Web服务、实时对话界面。
"""
url = f"{self.base_url}/api/chat"
payload = {
"model": model,
"messages": messages,
"stream": True,
}
async with httpx.AsyncClient(timeout=120.0) as client:
async with client.stream("POST", url, json=payload) as response:
response.raise_for_status()
async for line in response.aiter_lines():
try:
chunk = json.loads(line)
content = chunk.get("message", {}).get("content", "")
if content:
yield content
except json.JSONDecodeError:
continue
# ---------- 工具方法 ----------
def list_models(self) -> list[dict]:
"""列出本地已安装的模型。"""
url = f"{self.base_url}/api/tags"
with httpx.Client() as client:
response = client.get(url)
response.raise_for_status()
return response.json().get("models", [])
def pull_model(self, model_name: str) -> None:
"""
拉取模型(同步,会阻塞直到完成)。
如果需要进度,调用方可以改用异步流式版本。
"""
url = f"{self.base_url}/api/pull"
payload = {"name": model_name, "stream": False}
with httpx.Client(timeout=600.0) as client:
response = client.post(url, json=payload)
response.raise_for_status()
测试一下:
python
import asyncio
async def test_ollama():
client = OllamaClient()
msgs = [{"role": "user", "content": "什么是RAG?用两句话说清楚"}]
async for token in client.chat_stream("qwen2.5:7b", msgs):
print(token, end="", flush=True)
asyncio.run(test_ollama())
3.4 实战:模型选型对比实验
好了,现在来做真正有价值的事。同一台机器,部署两个不同尺寸的模型,跑同一组测试问题,然后填一份对比表。这一套你以后在自己项目里做模型选型,可以直接照搬。
3.4.1 拉取两个对比模型
bash
# 7B版本(主力)
ollama pull qwen2.5:7b
# 1.5B轻量版本(对比用)
ollama pull qwen2.5:1.5b
1.5B版本只有约1GB大小,内存占用小,但回答质量会有所下降。具体差距多少?数据说话。
3.4.2 编写对比测试脚本
python
"""
model_benchmark.py
对比不同模型在相同问题上的表现
本文件对应 stage01_env/model_benchmark.py
"""
import asyncio
import time
from ollama_client import OllamaClient
# 测试问题集:覆盖不同难度和类型
TEST_QUESTIONS = [
# 简单事实型
"什么是Java的垃圾回收机制?",
# 知识解释型
"请解释微服务架构中的服务发现原理",
# 代码生成型
"用Python写一个快速排序函数,带注释",
# 逻辑推理型
"如果数据库查询变慢,可能有哪些原因?",
# 中文理解型
"请用中文总结Spring Boot的三大核心特性",
]
MODELS = ["qwen2.5:7b", "qwen2.5:1.5b"]
async def benchmark_single_model(client: OllamaClient,
model: str,
questions: list[str]) -> list[dict]:
"""对单个模型跑全部测试问题,返回带性能数据的结果。"""
results = []
for i, question in enumerate(questions):
print(f" [{model}] 测试 {i+1}/{len(questions)}: {question[:40]}...")
messages = [{"role": "user", "content": question}]
start = time.perf_counter()
full_response = ""
token_count = 0
first_token_time = None
async for token in client.chat_stream(model, messages):
if first_token_time is None:
first_token_time = time.perf_counter()
full_response += token
token_count += 1
end = time.perf_counter()
total_time = end - start
ttft = first_token_time - start if first_token_time else 0
results.append({
"question": question,
"model": model,
"response": full_response,
"total_time_sec": round(total_time, 2),
"first_token_sec": round(ttft, 2),
"token_count": token_count,
# tokens/s 计算(排除首个token等待)
"tokens_per_sec": round(
(token_count - 1) / (total_time - ttft), 2
) if total_time > ttft and token_count > 1 else 0,
})
# 每个问题之间休息1秒,避免显存/CPU飙满
await asyncio.sleep(1)
return results
def print_comparison_table(all_results: dict[str, list[dict]]):
"""打印对比汇总表。"""
print("\n" + "=" * 80)
print("模型选型对比报告")
print("=" * 80)
for model in MODELS:
results = all_results[model]
avg_total = sum(r["total_time_sec"] for r in results) / len(results)
avg_ttft = sum(r["first_token_sec"] for r in results) / len(results)
avg_tokens = sum(r["token_count"] for r in results) / len(results)
avg_tps = sum(r["tokens_per_sec"] for r in results) / len(results)
print(f"\n📦 模型: {model}")
print(f" 平均总耗时: {avg_total:.2f} 秒")
print(f" 平均首token延迟: {avg_ttft:.2f} 秒")
print(f" 平均回复长度: {avg_tokens:.0f} tokens")
print(f" 平均生成速度: {avg_tps:.2f} tokens/s")
# 定性对比展示(取第一个问题的回答作为样例)
print("\n" + "-" * 40)
print("定性对比(第1题回答节选)")
print("-" * 40)
q0 = TEST_QUESTIONS[0]
for model in MODELS:
resp = all_results[model][0]["response"]
print(f"\n[{model}] {q0}")
# 截取前200字
print(f" → {resp[:200]}...")
async def main():
client = OllamaClient()
# 确保模型已安装
installed = [m["name"] for m in client.list_models()]
for model in MODELS:
if model not in installed:
print(f"模型 {model} 未安装,正在拉取...")
client.pull_model(model)
all_results = {}
for model in MODELS:
print(f"\n▶ 开始测试模型: {model}")
all_results[model] = await benchmark_single_model(
client, model, TEST_QUESTIONS
)
print_comparison_table(all_results)
if __name__ == "__main__":
asyncio.run(main())
3.4.3 运行对比测试
bash
cd stage01_env
python model_benchmark.py
刚开始跑,1.5B版本速度会明显快,7B版本会明显慢(尤其是8GB内存的机器上)。最终你会得到类似这样的对比表:
text
📦 模型: qwen2.5:7b
平均总耗时: 12.35 秒
平均首token延迟: 2.10 秒
平均回复长度: 218 tokens
平均生成速度: 21.5 tokens/s
📦 模型: qwen2.5:1.5b
平均总耗时: 4.20 秒
平均首token延迟: 0.60 秒
平均回复长度: 145 tokens
平均生成速度: 40.3 tokens/s
然后看定性部分:7B的回答更完整、更准确,尤其是"逻辑推理型"问题上差异明显;1.5B会偏简短,有时会跑题或遗漏关键点。
3.5 结论与选型建议
这张对比表直接告诉我们什么时候该选什么模型:
| 场景 | 推荐 | 理由 |
|---|---|---|
| 本地开发测试 | 1.5B | 启动快、不卡机、能验证链路是否通 |
| 生产问答 | 7B或更大 | 质量明显更优,用户愿意等2秒 |
| 实时对话/嵌入式 | 1.5B | 首token延迟低,体感流畅 |
| 批量数据处理 | 7B | 单次质量优先 |
当然这台机器的实际表现取决于你的CPU(GPU)、内存。后续我们在第5篇开始构建RAG核心时,我会把Embedding模型也纳入类似对比,让你对整个AI链路里每一步的模型选型都心里有数。
3.6 常见问题
Q:8GB内存能跑7B吗?
能,但跑起来后系统会频繁换页,生成速度掉到个位数token/s。建议至少16GB。
Q:想用GPU加速怎么办?
Ollama检测到NVIDIA显卡会自动启用CUDA。如果是Mac M系列芯片,会自动用Metal。使用 ollama ps 可以看当前模型是否在用GPU。
Q:模型下载太慢?
可以设置代理或使用国内镜像。另外有人会分享模型文件的离线包,用 ollama create 从本地文件导入,具体可查Ollama文档。
本篇文章源码:
-
stage01_env/ollama_client.py— Ollama客户端封装 -
stage01_env/model_benchmark.py— 模型选型对比脚本
AtomGit 是由开放原子开源基金会联合 CSDN 等生态伙伴共同推出的新一代开源与人工智能协作平台。平台坚持“开放、中立、公益”的理念,把代码托管、模型共享、数据集托管、智能体开发体验和算力服务整合在一起,为开发者提供从开发、训练到部署的一站式体验。
更多推荐



所有评论(0)