共计 3274 个字符,预计需要花费 9 分钟才能阅读完成。
很多极客在家里或工作室折腾 NAS,把原本只用来做 RAID 存相片、跑影视库的机器升级成了塔式或机架服务器,甚至塞进了一张二手 RTX 3090 或者 RTX 4060 Ti 16G。接着兴冲冲地拉起 Ollama 跑大模型,却很快遇到几个典型撞墙场景:多人并发访问请求直接排队超时;RAG 知识库切片解析时显存暴涨导致 OOM 被内核强杀;稍微长一点的上下文,吞吐直接暴跌到几个 Token/s。
本文不谈套话,直接端出我在自建 NAS(TrueNAS Scale / Ubuntu Server 底座)上长期稳定运行的一套高吞吐方案:vLLM 推理引擎 + Qwen2.5(通义千问 2.5)+ Dify 工作流与知识库系统。这一套组合拳能把消费级显卡的显存压榨到极致,长上下文不卡顿,且完美支持团队局域网内的高并发并发调用。
一、为什么放弃 Ollama 转向 vLLM?
Ollama 对小白极其友好,一条命令就拉起来。但在 NAS 这种常年后台挂载、往往需要充当小型私有 API 网关的场景下,Ollama 暴露出了几个硬伤:
- 内存与显存管理粗放:KV Cache 无法做到极致细粒度复用,面对长文档问答(RAG)显存碎片化严重。
- 并发吞吐表现一般:当家庭内部或小团队多人同时向模型发 Prompt,Ollama 底层走的是串行或简单的多实例机制,排队感明显。
- vLLM 的降维打击:利用 PagedAttention 算法,将 KV Cache 当成操作系统的虚拟分页来管理,显存浪费率直接降至 4% 以下。同时支持 Continuous Batching(连续批处理),并发场景下的 Throughput(吞吐量)通常是普通引擎的 3 到 6 倍。
二、硬件准备与 NVIDIA Docker 环境压测打底
如果你的 NAS 是 TrueNAS Scale 或自建的 Linux 系统,建议显卡至少 8GB 显存起步(推荐 16G 或 24G,比如 RTX 4060 Ti 16G 或 RTX 3090/4090)。群晖用户如果外接显卡拓展柜,请确保 PCIe 直通与驱动正常。
第一步,验证你的宿主机能够正确透传显卡到 Docker:
# 检查 Nvidia 驱动是否正常
nvidia-smi
# 确保 nvidia-container-toolkit 已就位
docker run --rm --gpus all nvidia/cuda:12.4.1-base-ubuntu22.04 nvidia-smi
如果容器内部正确打出了显卡型号和显存信息,环境就稳了一半。如果报 could not select device driver,说明系统的nvidia-ctk runtime configure --runtime=docker 没有执行,或者 Docker 守护进程未重启。
三、vLLM 轻量化拉起 Qwen2.5 实战配置
Qwen2.5 开源系列在中文、代码和长文本理解上表现极为优秀。对于 16G 显存的显卡,我们选择 Qwen/Qwen2.5-7B-Instruct-GPTQ-Int4 或者 AWQ 量化版本,显存占用仅 6GB 左右,剩下的 10GB 全留给长上下文的 KV Cache;如果是 24G 显存(如 3090),甚至可以直接跑 BF16 全精度的 7B 或者 GPTQ 版本的 14B/32B。
我们在 NAS 的工作目录下创建docker-compose.vllm.yml:
version: '3.8'
services:
vllm:
image: vllm/vllm-openai:v0.6.3
container_name: nas-vllm-server
runtime: nvidia
restart: always
environment:
- HUGGING_FACE_HUB_TOKEN=your_token_if_needed
ports:
- "8000:8000"
volumes:
# 将 NAS 上的高速 SSD 挂载为模型缓存目录,避免容器重建重复拉取
- /mnt/fast-pool/ai-models:/root/.cache/huggingface
ipc: host
deploy:
resources:
reservations:
devices:
- driver: nvidia
count: all
capabilities: [gpu]
command: >
--model Qwen/Qwen2.5-7B-Instruct-AWQ
--quantization awq
--served-model-name qwen2.5-7b
--max-model-len 16384
--gpu-memory-utilization 0.88
--enforce-eager
--trust-remote-code
核心参数避坑解析:
--gpu-memory-utilization 0.88:我在测试时踩过大坑,如果直接拉满到 0.95,当并发突然冲高或者操作系统有轻微图形输出时,直接 CUDA OOM。留出 12% 的缓冲空间是最稳妥的。--max-model-len 16384:Qwen2.5 支持高达 128K 上下文,但在 NAS 上切忌无脑设为 128K!128K 上下文会瞬间吃干所有 KV Cache,导致并发数直接跌到 1。在个人知识库场景下,16384(16K)完全够吃下几十页 PDF,同时保证 8 个以上并发顺畅流转。--enforce-eager:开启 Eager 模式能大幅缩短启动时的 CUDA 图捕捉时间,对于显存受限的环境特别管用,可以节约将近 500MB 临时显存开销。
四、接入 Dify 知识库与向量模型协同
模型跑起来后,vLLM 会在 8000 端口暴露标准的 OpenAI 兼容接口(http://<NAS-IP>:8000/v1)。接下来我们联动在 NAS 上跑的 Dify 应用。
在 Dify 后台的“模型供应商”中配置:
- 添加 OpenAI-API-compatible 协议。
- 模型类型:LLM。
- 模型名称 :
qwen2.5-7b(必须与启动命令中的--served-model-name完全一致)。 - API Endpoint URL:
http://nas-vllm-server:8000/v1(如果与 Dify 在同一 Docker 网络下),或填写 NAS 局域网 IP。 - API Key:若 vLLM 未配置
--api-key,此处可随意输入占位字符(如EMPTY)。
为了让整个知识库全链路离线可用,Embedding 模型推荐使用轻量且语义打分强悍的 BAAI/bge-large-zh-v1.5 或bge-m3。你可以选择用 CPU 跑 Text-Embeddings-Inference(TEI),把宝贵的 GPU 显存全部留给 vLLM 生成推理,形成“CPU 做文档向量化检索 + GPU 做生成解答”的黄金算力分配方案。
五、性能实测:吞吐与并发表现
我在一台配置了 Intel i5-13500 + 单张 RTX 3090(24G)的自建 NAS 上进行了压测对比,加载一份 4 万字的系统架构手册进行多轮并发提问:
| 推理后端方案 | 单并发 Token 速率 | 10 并发吞吐量 (Throughput) | 显存占用率 | 长上下文 OOM 概率 |
|---|---|---|---|---|
| Ollama (Qwen2.5-7B) | ~42 tokens/s | ~68 tokens/s(排队严重) | 动态分配(波动大) | 偶发 |
| vLLM (AWQ + PagedAttention) | ~65 tokens/s | ~240 tokens/s | 稳定在 88%(预分配锁定) | 0%(严格受控) |
实测数据一目了然:在单一用户低负载下两者体验差别不大;但一旦你的 NAS 同时跑了外部 Webhook 自动化、多位团队成员在 Dify 里调试 Prompt,vLLM 凭借持续批处理直接把整张显卡的算力吃透,几乎感受不到排队停顿。
总结与避坑心得
在私有云存储上玩 AI,最忌讳的是“贪大”。盲目追求 70B 量化模型往往导致 NAS 频繁死机、风扇狂啸且推理慢如蜗牛。经过长期压测验证,单卡 / 双卡优先锁死 8B 或 14B 级别的最新开源顶流(如 Qwen2.5、Llama-3.1),搭配 vLLM 限制合理上下文长度,再配合精细化的 RAG 切片策略,是当前个人极客与微型工作室性价比最高、稳定性最强的大模型本地私有化落地路径。
把你的 NAS 从单一的存储仓库,改造成局域网高可用的私有 AI 算力节点,现在就可以照着配置开干了。