
1. 为什么非要把 Harness 扔到服务器上1.1 本机跑的三个痛点逼我做了这个决定先说结论DeepSeek Harness 这玩意儿从一开始就不适合装在自己电脑上。我第一次在本机跑的时候用的是 MacBook Pro M1 Pro。安装倒是不费劲一条命令的事但真正用起来就开始头大了。首先是资源占用Harness 本身是一个带着调度引擎、上下文管理、工具调用协议和其他依赖组件的整套框架启动之后光是 node 进程和 Python 守护进程就能吃掉三四个 G 内存。再叠加我日常要开的 IDE、浏览器几十个标签页、微信和企业通讯工具电脑直接进入风扇狂转模式。第二个痛点是访问方式。本机跑的 Harness别人想用就得在你电脑上开端口、开共享先不说 firewall 那一堆配置有多烦单是你把电脑开着别关这句话就足够让同事打消尝试的念头。第三个痛点是模型来源。Harness 的价值在于它能把 DeepSeek 的模型能力统一接管起来但你不可能让每个人都在自己电脑上单独拉一份模型权重。模型文件动辄十几 G让研发团队五六个人各自下载一遍先不说网速光磁盘空间就是浪费。所以把 Harness 部署到一台常驻服务器上几乎是唯一合理的选择。部署完成之后团队所有人只要打开浏览器输入服务器地址就能直接使用统一的入口。这其实就是把 Harness 当成了一个完整的基础设施来运营。1.2 选了哪条部署路径为什么不是裸机直装决定上服务器之后接下来就是选部署方式。我圈定了三个候选裸机直装、Docker 部署、Docker Compose 编排。裸机直装最大的问题是环境隔离难做。Harness 依赖的运行时版本和系统自带的可能有冲突一旦哪天要在同一台服务器上跑其他服务依赖地狱马上就会出现。而且后续如果想升级 Harness 版本裸机直装需要手动停服务、备份配置、覆盖文件、重新起服务中间哪个环节手抖一下服务就起不来了。所以我最终选了 Docker Compose。核心原因是它的配置即代码整个部署过程可以被完整记录到docker-compose.yml文件里下次在任何一台新服务器上复现部署只需要把这份文件拷过去然后执行docker compose up -d。相比之下如果是裸机直装部署步骤散落在十几条命令和手动操作里没法版本化管理。另外一个很实际的原因是模型服务的接入。Harness 本身不直接持有模型权重它需要通过 API 方式对接一个模型运行时服务。在我这个方案里模型运行时用的就是 Ollama 的 Docker 版本然后在同一个 Compose 网络里让 Harness 容器通过http://ollama:11434访问模型服务。容器之间用服务名互通这套玩法只有在 Compose 里才最顺滑。2. 部署前的准备硬件、系统和容器环境2.1 服务器硬件配置建议别在这上面省钱Harness 对硬件的要求本质上是看它管理的模型有多大。以 DeepSeek 的 7B 参数模型为例如果用 FP16 精度运行光是模型权重就需要大概 14GB 显存加上 KV Cache 和上下文窗口的额外开销一张 24GB 显存的显卡是起步线。我这次用的是公司一台闲置的深度学习服务器配置如下项目配置说明CPUIntel Xeon Gold 6230双路主要负责调度和数据处理内存128GB DDR4 ECC给上下文缓存和并发会话用GPUNVIDIA RTX 3090 24GB 两张一张跑模型一张给并发补位系统盘512GB NVMe SSD装系统和 Docker 镜像数据盘2TB NVMe SSD存模型权重和日志系统Ubuntu 22.04 LTS长期支持版本稳如果你手头预算有限至少要保证显卡有 24GB 显存。我实测下来 7B 模型在量化到 Q4 之后能压到 6GB 左右但那种压缩会明显损失输出质量尤其是在代码生成这种对准确性要求高的场景跑出来的代码错漏明显变多。所以宁可多花点钱上大显存也别在硬件上将就。如果你想跑 DeepSeek 的 34B 或者更大的 MoE 版本24GB 就有点不够用了至少需要两张 24GB 显卡做模型并行或者直接用量化版本。这些方案我都试过部署思路完全一样只是模型拉取和启动加载的时间会显著变长。2.2 Ubuntu 系统初始化和 Docker 环境搭建拿到服务器后先做基础的系统初始化。我习惯第一步先更新软件源并安装基础工具新服务器一般没有这些包sudo apt update sudo apt upgrade -y sudo apt install -y curl git vim net-tools htop tmux接着安装 Docker。Ubuntu 上直接apt install docker.io虽然也能装但版本往往偏旧所以我更推荐用 Docker 官方脚本安装能保证拉到当前稳定版本curl -fsSL https://get.docker.com | bash -s docker这里有一个重要经验安装完 Docker 之后默认情况下普通用户不能直接执行 docker 命令需要加 sudo。为了避免每次操作都要 sudo要把当前用户加入 docker 用户组sudo usermod -aG docker $USER改完之后重新登录终端才能生效。然后顺手把 Docker Compose 插件装上并验证一下版本sudo apt install -y docker-compose-plugin docker compose version最后强烈建议配置 Docker 镜像加速器不然拉取镜像的时候能等到怀疑人生。在/etc/docker/daemon.json里写入镜像源配置然后重启 Docker 服务。这一步我每次部署新服务器都会做踩过一次干等十分钟都拉不下来镜像的坑之后就再也不敢省这一步了。3. Harness 部署实操全流程照着抄就行3.1 项目目录规划和配置文件编写部署的第一步不是急着拉镜像而是把目录结构规划好。一个清晰的项目目录后续维护和排查问题都会省心很多。我是这样建的mkdir -p /opt/deepseek-harness/{data,logs,models,config} cd /opt/deepseek-harness我的习惯是data目录存 Harness 的业务数据包括会话记录、任务队列、用户配置logs目录挂载给各容器输出日志排查问题时直接看宿主机上的文件models目录留给 Ollama 存模型权重这样做的好处是即使容器被删掉重建模型也不用重新下载config目录放 Harness 的配置文件和环境变量目录结构出来之后开始写docker-compose.yml。这是整个部署的核心文件我把常用配置贴出来并逐项解释version: 3.8 networks: harness-net: driver: bridge volumes: redis-data: driver: local services: ollama: image: ollama/ollama:latest container_name: ollama restart: always volumes: - /opt/deepseek-harness/models:/root/.ollama ports: - 11434:11434 networks: - harness-net deploy: resources: reservations: devices: - driver: nvidia count: 1 capabilities: [gpu] redis: image: redis:7-alpine container_name: harness-redis restart: always command: redis-server --requirepass yourpassword --maxmemory 2gb --maxmemory-policy allkeys-lru volumes: - redis-data:/data networks: - harness-net harness: image: deepseek/harness:latest container_name: deepseek-harness restart: always depends_on: - ollama - redis ports: - 8080:8080 - 8081:8081 environment: - HARNESS_MODEL_ENDPOINThttp://ollama:11434 - HARNESS_MODEL_NAMEdeepseek-coder:7b - HARNESS_REDIS_URLredis://:yourpasswordredis:6379 - HARNESS_AUTH_ENABLEDtrue - HARNESS_MAX_CONCURRENT_SESSIONS20 - HARNESS_CONTEXT_LIMIT8192 volumes: - /opt/deepseek-harness/data:/app/data - /opt/deepseek-harness/logs:/app/logs - /opt/deepseek-harness/config:/app/config networks: - harness-net这份配置里有几个关键点值得展开讲。Connector 部分配置里deploy.resources.reservations这一段是 GPU 资源声明它的作用就是告诉 Docker 这个容器需要挂载 NVIDIA GPU。注意这个配置得配合 NVIDIA Container Toolkit 才能生效否则就算 GPU 驱动装了容器里也感知不到显卡的存在。NVIDIA Container Toolkit 的安装方式不同版本的 Ubuntu 略有差异如果遇到容器里nvidia-smi报错第一件事就是检查这个工具链是否装好。第二个关键点是 Redis 的maxmemory参数。我一开始用的是默认配置结果跑了一天后 Redis 内存暴涨到 6GB。原因是 Harness 会把会话历史、任务状态都往 Redis 里写如果没有内存上限和淘汰策略Redis 会一直吃内存直到系统 OOM。加上maxmemory 2gb和allkeys-lru之后老会话会被自动清理新会话不受影响。第三个点是端口规划。Harness 有两个端口8080 是主服务端口提供 Web 管理界面和 API 入口8081 是内置的监控端口可以拉取运行指标。后面接监控面板或者告警系统时8081 上的/metrics端点可以直接被 Prometheus 抓取省了额外写 exporter 的功夫。3.2 启动模型服务和验证 Ollama 连通性先不要急着把 Harness 整个启动分步走能帮你快速定位问题。第一步先把 Ollama 单独启动起来并拉取模型cd /opt/deepseek-harness docker compose up -d ollama docker compose logs -f ollama看到 Ollama 正常启动后拉取模型。这里的选择很有讲究我最初直接拉deepseek-coder:7b拉取过程大概十几分钟取决于网速。下载完成之后执行一下模型验证docker exec -it ollama ollama run deepseek-coder:7b 写一个 Python 函数实现快速排序如果模型能正常返回代码片段说明 Ollama 服务正常GPU 驱动也生效了。这里有个小技巧查看容器日志如果里面有类似 CUDA 的初始化日志就说明 GPU 确实被容器用上了。3.3 启动完整栈第一次访问 Harness 界面模型服务通了之后就把整个 Compose 栈拉起来docker compose up -d docker compose ps正常情况下能看到三个容器都是 running 状态。这时候打开浏览器访问http://服务器IP:8080就能看到 Harness 的 Web 管理界面。第一次打开界面需要做初始化配置包括设置管理员账号密码、配置模型路由规则、设置会话并发上限。这些都可以在界面上操作不需要改配置文件。我自己习惯把默认模型设成刚才拉取的deepseek-coder:7b这样同事打开就能直接用不需要手动选模型。我在实际部署中还加了一层 Nginx 反向代理把 8080 端口映射到标准的 443 HTTPS 端口这样同事们就不用记带端口号的地址。如果你也打算这么做注意在 Nginx 里加上 WebSocket 的支持因为 Harness 的实时会话推送是基于 WebSocket 的默认配置下代理会丢掉升级请求导致前端一直连接不上。代码大概是这样location / { proxy_pass http://127.0.0.1:8080; proxy_http_version 1.1; proxy_set_header Upgrade $http_upgrade; proxy_set_header Connection upgrade; proxy_set_header Host $host; proxy_read_timeout 3600s; }proxy_read_timeout我特意调大到了 3600 秒不然长上下文生成超过一分钟代理就会主动断开连接导致前端报网络错误。这个坑我踩了三次才定位到属于那种不看 Nginx 日志死活找不出来的问题。4. 同事们玩嗨了真实的使用场景和调优记录4.1 第一天开放使用大家最常拿来干嘛部署完成后的第一个工作日我在团队里简单发了个通知说内部的大模型入口挂在哪个地址大家有需要可以试试。结果当天的访问量远超我的预期下午高峰期同时有七八个会话在跑观察了一下使用场景主要集中在三个方向第一是代码生成和补全。研发同事把 Harness 当成了一个随时可以问的结对编程助手遇到不熟悉的 API 或者要写一些重复性高的模板代码直接打开 Harness 的对话框描述需求生成的代码基本可以直接用。这里要特别夸一下 DeepSeek Coder 模型在代码补全上的表现对于 Python 和 TypeScript 的支持尤其顺手上下文窗口内一次给个二三十行代码的补全质量相当能打。第二是日志和报错排查。运维和测试的同事把报错信息、完整的日志片段贴进去让模型帮忙分析可能的原因。这类请求通常文本比较长好在 Harness 的上下文管理机制做得好长文本会话可以自动总结前置关键信息不会像裸调模型那样上下文一长就丢信息。第三是文档和脚本撰写。非技术岗位的同事也会偶尔用一下比如让模型帮忙起草周报、总结会议纪要、生成数据处理脚本。这里不得不提一句敞开了让大家用之后很多需求是你提前想不到的比如有同事让模型帮忙写了个批量重命名文件的脚本还有让模型帮忙整理客户反馈的分类汇总表。工具的普及度上来了使用场景自然会发散。4.2 并发上来了性能瓶颈也能实时看到同事玩嗨了之后我的任务也从部署阶段切换到了运维阶段。通过 8081 端口上的监控接口我配置了一个简单的告警脚本每隔一分钟拉取一次指标当并发会话数超过 80% 时发一条通知到企业微信。实测下来的性能数据如下单张 RTX 3090 跑 7B 模型Q4 量化之后单会话生成速度能稳定在每秒 30 到 40 个 token这速度对于办公场景来说完全够用。当并发达到五个会话时生成速度会降到每秒 20 个 token 左右但还在可接受范围内。到十个并发以上速度明显下滑每个会话的响应时间会拖到半分钟左右。这个瓶颈主要卡在显存的 KV Cache 分配上。Harness 默认会根据显存大小自动调整 KV Cache 的容量但它对显存有比较保守的估计即便显存还有剩余也不会把缓存开满。后来我在 Harness 的配置里手动指定了 KV Cache 的分配比例把单张卡的缓存利用率从默认的 40% 调到了 60%并发能力明显提升峰值并发从五个涨到了八个左右生成速度也没有明显劣化。如果你也遇到并发瓶颈建议先看一眼监控指标确认到底是显存不够还是算力跑满再有针对性地调优不要盲目加卡。显存跑到 90% 以上就考虑调小 KV Cache 或者上第二张卡算力跑满则优先考虑换更大的显存卡。5. 常见问题与排查技巧实录5.1 部署和运行中的 Top 6 问题速查表这些天运维下来我整理了一批高频问题及对应的排查思路都以表格形式总结如下问题现象可能原因排查与解决方法容器启动后立刻退出端口占用了或者环境变量格式不对先看docker compose logs的具体报错端口占用用ss -lntp确认环境变量则检查是否有空格和特殊字符Harness 界面能打开但是发消息无响应Harness 和 Ollama 之间的网络不通或者模型没加载好docker compose exec harness curl http://ollama:11434测连通性再确认模型确实已经拉取完成回复速度特别慢GPU 没被容器使用模型跑在 CPU 上在 Ollama 容器里执行nvidia-smi如果报错说明 NVIDIA Container Toolkit 没装好上下文一长就开始胡说KV Cache 配太小长对话早期内容被抛弃调整 KV Cache 分配比例或者换更大显存的显卡Redis 内存持续增长会话历史堆积没有设置内存上限检查 Redis 是否加了maxmemory和allkeys-lru参数团队反馈浏览器一直转圈Nginx 反代未启用 WebSocket 支持检查反代配置中是否有Upgrade和Connection头信息除了表格里的内容我想单独再讲两个排查案例因为它们花了我比较长的时间。第一个案例是 Harness 界面能打开但是发消息之后前端一直显示连接中。查了好久发现是浏览器的 WebSocket 连接被 Nginx 层挡掉了。H2 升级请求到 Nginx 之后Nginx 默认直接当成普通 HTTP 处理没有把协议升级成 WebSocket导致前端一直在等待推送消息。这个问题从客户端看是Harnass 没反应但实际原因在代理层。第二个案例比较隐蔽Ollama 容器里nvidia-smi能正常输出但生成速度只有每秒几个 token。后来对比了宿主机和容器里的 CUDA 版本发现宿主机驱动较新但容器内自带的 CUDA 运行时是旧版本算力没有跑在最优状态。最后是把 Ollama 镜像升级到了带新 CUDA 运行时的新版本速度立刻恢复正常。5.2 运维中的三个独家经验第一备份和恢复策略一定要提前做。Harness 的数据包括配置、会话记录、日志等我每天凌晨三点用 cron 把整个data和config目录打包上传到对象存储保留最近七天的备份。恢复的时候只需要把备份拷贝回原目录然后docker compose restart全过程五分钟以内。第二日志别只存在容器里。Docker 的默认日志驱动会把容器输出写到宿主机但不会做轮转跑久了磁盘会被日志撑爆。我的方案是在daemon.json里配置 log rotation限制单个容器日志文件大小上限和保留数量这样日志最多占 500MB不会出现把磁盘写满的意外。第三任何改动前先快照。服务器如果是云主机操作前打个快照如果是物理机就把关键目录 tar 一份。有一次我手滑改了模型配置文件重启之后 Harness 一直起不来最后全靠回滚配置文件解决。现在我的习惯是改任何文件之前先cp xxx xxx.bak成本很低但省了无数麻烦。5.3 后续要扩展的方向现在的部署版本只能算基础版后续值得尝试的方向还有不少。比如接入更多模型做路由让 Harness 根据任务类型自动选择模型再比如把 Harness 的消息通过 Webhook 接到内部群里大家直接在群里发起生任务不用单独打开网页以及加上更细粒度的用户权限控制不同部门的人只能访问不同的模型和数据。我自己接下来打算先把用户管理做起来现在已经有人开始问能不能给外部客户开一个体验账号了。这方面的权限控制和数据隔离得提前想清楚再做不然出了合规问题就很麻烦。6. 最后聊几句大实话部署这套 Harness 整体上投入产出比很高从规划到上线大概花了一个周末的时间换来的是团队日常工作效率的明显提升。从我自己的体会出发有两点比较重要一是部署的时候分步验证别一股脑把整个栈拉起来再排错那会非常痛苦二是配置文件的每个参数都值得花时间弄清楚含义很多上线后的性能问题根源其实都出在初始化时一个默认参数上。如果你也正在计划给团队或者自己部署一套类似的模型服务强烈建议直接参考上面这套 Docker Compose 方案。整个过程最大的门槛其实不在技术而在耐心按步骤验证、看清日志、一个一个解决问题。把这个流程走通一次之后后续扩模型、加用户都只是配置文件里几行改动的事。