ARTICLE DETAIL

资讯详情

深耕郑州网站建设与运营推广的一线实战洞察。

在飞牛 NAS 上用 Docker 运行 DeepSeek Harness

在飞牛 NAS 上用 Docker 运行 DeepSeek Harness 在飞牛 NAS 上用 Docker 运行 DeepSeek Harness一、这是什么DeepSeek Harness下文简称 dsh是一个跑在本地、基于网页的 AI 工作台。它本身不提供模型而是把你已有的各种大模型 APIDeepSeek、OpenAI -compatible、Ollama 等聚合到一起统一管理 provider、预设preset、凭据和插件还能跑 agent。简单说它是一个「自己托管的 AI 操作台」配置一次 API Key之后在网页里切换不同模型、不同预设来对话支持插件和工作区agent 能直接读写文件数据全在自己机器上不依赖任何第三方 SaaS。因为官方没有放出成品镜像本文用的是社区维护的runzhliu/deepseek-harness镜像。二、部署完能怎么用部署好之后dsh 会作为一个应用出现在飞牛的 watchcow 面板里。点一下图标就能打开不用记 IP、不用记端口在外网通过飞牛分配给你的 watchcow 域名访问且必须先登录飞牛账号在局域网直接走https://你的 NAS 局域网 IP:端口打开。打开后就是 dsh 的主界面左边选 provider、配预设右边直接对话跟用本地软件一样。三、搭建步骤下面按步骤来。整体思路是用 docker-compose 起两个容器一个跑 dsh 本体只在内部网络不对外暴露一个跑 nginx 反代对外暴露端口、处理 HTTPS 和请求头改写最后用 watchcow 把入口收进飞牛面板。第 1 步准备目录和证书唉在存储池里建好 dsh 的数据目录和工作区目录例如你的存储池路径/docker/deepseek-harness/dshdsh 的数据目录API Key、会话、插件配置都存在这你的存储池路径/deepseek-harness工作区给 agent 读写文件用。证书方面飞牛系统里自带证书管理去飞牛的「证书」功能里把对应域名的证书下载/导出出来放进项目目录的certs/文件夹命名为fullchain.crt和private.key。后面 nginx 会用这两个文件在 443 上终止 TLS。注意飞牛 watchcow 网关对 https 服务做的是TLS 透传网关自己不解密流量所以证书必须挂在后面的 nginx 容器里而不是指望网关帮你处理。第 2 步在飞牛上装 watchcow 应用并绑定域名在飞牛应用中心装好 watchcow就是那个能把 docker 服务收进统一面板的工具。装好后给 dsh 预留一个域名在 watchcow 里添加应用时填写这个域名之后就是对外访问地址。这一步本质上是「先占好入口」后面的 docker 服务只要带对的 label就会被 watchcow 自动识别并挂上这个域名。第 3 步写 docker-compose新建一个目录放项目文件结构大致如下deepseek-harness/ ├── docker-compose.yml ├── config/ │ └── nginx-config.conf └── certs/ ├── fullchain.crt └── private.keydocker-compose.yml里定义两个服务deepseek-harness用runzhliu/deepseek-harness:0.1.0-rc.6镜像挂上面建好的两个目录不映射端口只在内部网络里跑nginx用nginx:alpine把宿主端口这里用11013映射到容器443挂上 nginx 配置和证书目录并带上 watchcow 的 label下面第 5 步细说。两个服务连同一个自定义的内部网络dsh 只在内部可达nginx 通过服务名deepseek-harness:3080访问它。完整docker-compose.ymlservices:deepseek-harness:image:runzhliu/deepseek-harness:0.1.0-rc.6container_name:deepseek-harnessrestart:alwaysnetworks:-dsh-internalvolumes:# 数据目录API Key、会话、插件配置都在这-你的存储池路径/docker/deepseek-harness/dsh:/home/node/.dsh# 工作区给 agent 读写文件用-你的存储池路径/deepseek-harness:/workspaceenvironment:-DSH_TELEMETRY_DISABLED1# 不映射 ports仅在内部网络可达nginx:image:nginx:alpinecontainer_name:dsh-nginxrestart:alwaysnetworks:-dsh-internalports:-11013:443# 飞牛网关 TLS 透传nginx 在 443 终止 TLSvolumes:-./config/nginx-config.conf:/etc/nginx/conf.d/default.conf:ro-./certs:/etc/nginx/certs:rodepends_on:-deepseek-harnesslabels:watchcow.enable:truewatchcow.display_name:deepseek-harnesswatchcow.icon:https://cdn.jsdelivr.net/gh/selfhst/icons/png/deepseek-dark.pngwatchcow.main.service_port:11013watchcow.main.protocol:httpswatchcow.main.title:dshwatchcow.main.all_users:falsewatchcow.main.ui_type:urlnetworks:dsh-internal:driver:bridge上面你的存储池路径替换成你自己的实际路径即可。第 4 步配 nginx 反代这是关键。dsh 有几道安全限制从外部直接反代会被拦所以 nginx 必须做两件事把请求头里的Host改写成127.0.0.1:3080骗过 dsh 的回环校验把Origin头剥掉dsh 在 Origin 不存在时直接放行。同时 nginx 要listen 443 ssl挂上第 1 步准备的证书并做好 WebSocket 升级头、长超时等配置AI 会话可能很久不断开。只改 Host 不剥 Origin或者只剥 Origin 不改 Host都会得到HTTP 403两个动作缺一不可。完整config/nginx-config.confupstream dsh_backend { server deepseek-harness:3080; keepalive 32; } server { listen 443 ssl default_server; ssl_certificate /etc/nginx/certs/fullchain.crt; ssl_certificate_key /etc/nginx/certs/private.key; ssl_protocols TLSv1.2 TLSv1.3; client_max_body_size 100m; location / { # 核心改写 Host 为回环 剥掉 Origin / Sec-Fetch proxy_set_header Host 127.0.0.1:3080; proxy_set_header Origin ; proxy_set_header Sec-Fetch-Site ; proxy_set_header Sec-Fetch-Mode ; # 标准反代头 proxy_set_header X-Real-IP $remote_addr; proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; proxy_set_header X-Forwarded-Proto https; proxy_set_header X-Forwarded-Host $host; # WebSocket 支持dsh 事件流 proxy_set_header Upgrade $http_upgrade; proxy_set_header Connection upgrade; # 长超时适配长时间 AI 会话 proxy_read_timeout 86400s; proxy_send_timeout 86400s; proxy_buffering off; proxy_pass http://dsh_backend; } }证书路径/etc/nginx/certs/...对应第 1 步挂进去的certs/目录。host头里的Sec-Fetch-*一并剥掉是为了让局域网用 IP 访问时不被判成跨站而拦掉。第 5 步配 watchcow 的 label在 nginx 服务上加 watchcow 相关的 label让面板识别它watchcow.enable: true开启识别watchcow.display_name面板里显示的名字watchcow.main.service_port填对外端口如11013watchcow.main.protocol填httpswatchcow.main.ui_type填url用新页面打开比 iframe 内嵌更稳局域网下也不会被证书问题卡住再配个watchcow.icon当图标。第 6 步启动在 compose 目录里启动dockercompose up-d启动后dsh 容器和 nginx 容器都会restart: always自动拉起。去 watchcow 面板看一眼deepseek-harness 应该已经出现在列表里了。第 7 步验证外网打开watchcow生成的应用(dsh),会跳转域名局域网打开https://你的 NAS 局域网 IP:11013浏览器可能会报证书不匹配因为证书是给域名签的点「继续访问」即可。能正常加载 provider 列表、能对话就说明整套通了。四、常见问题1. 页面能打开但一加载提供方目录 / 读取设置就报 403这是 dsh 的安全栅栏在拦。确认 nginx 同时做了Host → 127.0.0.1:3080改写和剥掉Origin头缺一不可。2. 网关直接报 502nginx 日志里一堆\x16\x03\x01这种乱码说明 nginx 在listen 80上收到了 HTTPS 握手字节。飞牛网关是 TLS 透传不会帮你解密必须让 nginx 在443 ssl上挂证书自己终止 TLS。3. dsh 容器一直重启 / 起不来nginx 那边 Host unreachable检查 dsh 数据目录里的.credentials.yaml文件权限必须是600。权限不对 dsh 启动即崩改成600即可。4. 局域网用 IP 访问时被拦cross-site在 nginx 里把Sec-Fetch-Site和Sec-Fetch-Mode头也一起剥掉dsh 就无法判定跨站而放行。另外建议ui_type用url而不是iframe内嵌在局域网下容易被证书问题卡住。5. 访问时浏览器说证书不安全证书是签给你域名的用 IP 访问时 CN 对不上属正常现象。点「继续访问 / 仍要发送」即可追求干净体验就用域名访问。部署完成之后平时要切模型、试预设、跑 agent点一下面板图标就进去了不用记端口也不用裸跑服务。dsh 这套安全限制在没搞明白之前确实容易卡很久但本质就是改写 Host 剥 Origin 两件事配好就稳了。
返回列表