ARTICLE DETAIL

资讯详情

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

Windows 本地部署 Dify 实战:Docker、WSL2 与 Flask 代理避坑指南

Windows 本地部署 Dify 实战:Docker、WSL2 与 Flask 代理避坑指南 简介这份资源是面向Windows平台开发者的Dify Hackathon环境部署文档适合具备Git、Docker与Python基础、准备参与Dify Hackathon或搭建本地大模型应用开发环境的技术爱好者。内容围绕前置环境准备、代码克隆、环境变量配置、docker-compose服务启动、数据库初始化与安装验证等环节展开并针对Docker启动失败、端口占用、服务无法访问等常见问题给出排查思路同时延伸至应用创建、模型集成与Hackathon开发等后续操作。资源包为1个docx文档约15KB以图文步骤形式组织便于按流程对照执行。目前已有125人学习适合希望快速在Windows下跑通Dify本地环境、减少部署踩坑的开发者参考。1. Windows 上跑 Dify为什么我劝你先别急着双击安装包如果你在 Windows 上搜 Dify 安装大概率会看到两种答案一种是让你装 Docker Desktop 然后一条命令拉起另一种是让你老老实实配 Python 环境、拉源码、跑 Flask。这两条路我都走过结论是——在 Windows 上部署 DifyDocker 是主线Python 源码是备胎Git 是你全程都要用的工具。Dify 本身是一个开源的 LLM 应用开发平台能拖拽编排工作流、挂知识库、接各种模型 API社区版功能已经够一个小团队内部用。但它的官方部署文档默认你是 Linux 环境Windows 下有一堆路径、权限、端口、WSL 的坑等着你。这篇不是官方文档翻译是我自己在一台 Windows 11 机器上从零把 Dify 跑起来、又踩了几轮坑之后的记录适合想本地部署 Dify 做工作流验证、又不想折腾 Linux 双系统的后端或全栈。下面从环境准备讲到插件安装和升级每一步都给你能直接抄的命令。2. 环境准备Docker Desktop、WSL2 与 Git 的版本选择2.1 为什么 Dify 在 Windows 上必须走 DockerDify 的社区版部署包里包含 API 服务、Worker、Web 前端、PostgreSQL、Redis、Weaviate 或 Qdrant 向量库、Nginx 这一整套。你如果手动一个个装光是 PostgreSQL 和 Redis 在 Windows 上的原生支持就够你喝一壶。官方提供的docker-compose.yaml把这些组件的镜像、网络、卷、环境变量全编排好了你只需要保证 Docker 能跑。Windows 上跑 Docker 有两条路一是 Docker Desktop 配合 WSL2 后端二是直接在 WSL2 的 Linux 发行版里装 Docker Engine。我推荐前者因为 Docker Desktop 的图形界面在排查容器状态时省事而且端口映射到 Windows 宿主机是自动的你在浏览器里直接访问localhost就行。后者虽然更“干净”但每次都要进 WSL 终端操作对不熟悉 Linux 的人反而增加心智负担。版本上Docker Desktop 建议 4.30 以上它内置的 Docker Compose V2 对docker compose子命令支持更完整。WSL2 内核更新到最新否则 Docker Desktop 启动时可能卡在 “Starting the Docker Engine”。Git 用 2.40 以上因为 Dify 的部署脚本里有些git clone和子模块操作老版本 Git 在 Windows 路径处理上偶尔会抽风。2.2 安装 Docker Desktop 与开启 WSL2 的具体步骤先确认你的 Windows 版本。WinR 输入winver版本号要 21H2 及以上家庭版也能用 WSL2。然后以管理员身份打开 PowerShell执行下面两条命令开启所需功能# 启用 WSL 和虚拟机平台功能这两条是 Docker Desktop 的硬前提 dism.exe /online /enable-feature /featurename:Microsoft-Windows-Subsystem-Linux /all /norestart dism.exe /online /enable-feature /featurename:VirtualMachinePlatform /all /norestart执行完重启电脑。重启后下载 WSL2 内核更新包并安装然后在 PowerShell 里把默认版本设为 2# 将 WSL 默认版本设为 2Docker Desktop 必须用 WSL2 后端 wsl --set-default-version 2 # 查看当前 WSL 状态确认没有报错 wsl --status接下来去 Docker 官网下载 Docker Desktop for Windows 的安装包双击安装。安装时勾选 “Use WSL 2 instead of Hyper-V”不要勾选 “Add shortcut to desktop” 以外的多余选项。装完启动 Docker Desktop右下角托盘图标变成绿色鲸鱼且不再闪烁说明引擎就绪。这里有个参数值得注意Docker Desktop 默认给 WSL2 分配的内存是宿主机的一半。如果你机器只有 8GB 内存Dify 全套容器跑起来会非常吃力PostgreSQL 和向量库都可能因为 OOM 被 kill。解决办法是在用户目录下建一个.wslconfig文件# 放在 C:\Users\你的用户名\.wslconfig [wsl2] memory6GB processors4 swap2GB改完在 PowerShell 执行wsl --shutdown再重启 Docker Desktop 生效。这个文件是 WSL2 的全局配置不是 Docker 专属但直接影响容器能用的资源上限。2.3 Git 拉取 Dify 源码与目录规划Dify 的部署方式有两种一种是直接下载 release 里的 docker-compose 包另一种是git clone主仓库然后进docker目录。我建议用 Git 克隆因为后续升级、看配置变更、切分支都方便。选一个路径不要太深的目录比如D:\projects。Windows 的路径长度限制虽然在新版已经放宽但 Docker 挂载卷时如果路径里有中文或空格偶尔会出现挂载失败。执行# 克隆 Dify 主仓库--depth 1 只拉最新一次提交省时间 git clone --depth 1 https://github.com/langgenius/dify.git D:\projects\dify # 进入 docker 部署目录所有编排文件都在这里 cd D:\projects\dify\docker克隆完成后你会看到.env.example、docker-compose.yaml、nginx目录等。.env.example是环境变量模板下一步要复制成.env再改。这里注意不要直接在.env.example上改升级时这个文件会被覆盖你的配置就丢了。复制命令# 复制环境变量模板后续所有密钥和端口配置都改这个文件 copy .env.example .env到这一步环境准备就算完成。Docker 引擎在跑源码在本地环境变量文件已就位。下一章进入真正的启动和配置环节。3. 启动 Dify.env 关键参数与容器编排实操3.1 .env 里必须改的五个参数.env文件里参数上百个但初次部署真正影响能不能跑起来、能不能从外部访问的就下面这几个。用记事本或 VS Code 打开.env逐项确认。第一个是EXPOSE_NGINX_PORT默认 80。如果你 Windows 上已经装了 IIS 或者别的占用了 80容器启动时 Nginx 会报端口冲突。改成 8080 或别的空闲端口。第二个是SECRET_KEY这是 Dify 用来签名会话的默认值是个占位符必须换成一串随机字符。用 Python 生成一个# 生成一个 42 位的随机密钥复制到 .env 的 SECRET_KEY import secrets print(secrets.token_urlsafe(42))第三个是数据库密码POSTGRES_PASSWORD默认difyai123456。本地玩无所谓但只要这台机器在局域网里能被别人访问就一定要改。第四个是CONSOLE_API_URL和CONSOLE_WEB_URL如果你只在本机用localhost访问保持默认空值即可如果你想让同局域网的其他机器访问要填宿主机的 IP比如http://192.168.1.100:8080否则前端会请求不到 API。第五个是向量库选择Dify 默认用 Weaviate.env里VECTOR_STORE变量控制。如果你机器内存紧张可以改成qdrantQdrant 的资源占用比 Weaviate 低一些但需要把docker-compose.yaml里对应的服务启起来。改完.env后有一个容易忽略的点docker-compose.yaml里很多服务通过env_file读取.env但 Compose 在解析时对变量替换的时机有要求。如果你在.env里写了带空格的值比如CONSOLE_API_URLhttp://192.168.1.100:8080不要加引号加了引号在某些 Compose 版本里会把引号也当成值的一部分。3.2 docker compose up 的正确姿势与首次启动观察在D:\projects\dify\docker目录下打开 PowerShell执行# -d 后台运行首次启动会拉取所有镜像视网速需要 5-15 分钟 docker compose up -d首次执行会从 Docker Hub 拉取 postgres、redis、weaviate、nginx、dify-api、dify-web 等镜像。如果卡在某一层不动大概率是网络问题可以配置 Docker Desktop 的镜像加速器在 Settings → Docker Engine 里加 registry-mirrors。拉取完成后容器会依次启动但注意容器启动顺序不代表服务就绪顺序。PostgreSQL 初始化需要时间API 服务如果比数据库先起来会反复重试连接日志里刷connection refused这是正常的等一两分钟就好。用下面命令观察状态# 查看所有容器状态STATUS 列显示 Up 且没有 Restarting 才算稳 docker compose ps # 跟踪 api 服务日志看到 Application startup complete 才算真正就绪 docker compose logs -f api当api日志出现Application startup complete并且docker compose ps里所有服务都是Up状态就可以打开浏览器访问http://localhost:8080如果你改了端口就换成对应端口。第一次访问会让你设置管理员账号填邮箱和密码这个账号是存在 PostgreSQL 里的后续升级不会丢。3.3 验证部署是否成功的三个检查点第一个检查点前端页面能正常加载登录后能看到「探索」「工作室」「知识库」这些菜单。如果页面白屏按 F12 看 Console大概率是CONSOLE_API_URL配错了前端请求 API 跨域被拦。第二个检查点在「设置 → 模型供应商」里能添加一个模型。Dify 本身不带模型你需要填 OpenAI 兼容的 API Key 和 Base URL。如果保存时报错看api容器日志常见的是网络不通或者 Key 格式不对。第三个检查点创建一个空白应用选「工作流」类型随便拖一个开始节点和一个结束节点点运行。如果能在几秒内返回结果说明 API、Worker、数据库、Redis 这条链路全通了。这一步是端到端验证比看容器状态更可靠。提示如果docker compose ps里某个容器一直Restarting先看它的日志docker compose logs 服务名八成是环境变量缺失或端口冲突不要急着重装。4. 避坑与排查Windows 下 Dify 部署的五个血泪经验4.1 端口冲突导致 Nginx 反复重启现象docker compose ps里 nginx 容器状态是Restarting日志报bind() to 0.0.0.0:80 failed (98: Address already in use)。原因Windows 宿主机上 80 端口被 IIS、Skype 或者某些后台服务占了。Docker Desktop 的端口映射是把容器端口绑到宿主机端口宿主机端口被占就直接失败。解决先用netstat -ano | findstr :80找到占用进程的 PID再tasklist | findstr PID看是什么程序。如果是 IIS去服务里停掉如果不想动别的服务就改.env里的EXPOSE_NGINX_PORT8080然后docker compose down再up -d。改完记得浏览器访问也要带新端口。4.2 WSL2 内存不足导致容器被 OOM Kill现象用着用着 Dify 突然打不开docker compose ps里 postgres 或 weaviate 不见了docker compose logs显示Killed。原因WSL2 默认最多用宿主机一半内存Dify 全套跑起来峰值能到 4-5GB。8GB 机器上如果同时开浏览器和 IDE很容易触发 OOM。解决按 2.2 节说的建.wslconfig限制内存并加 swap或者关掉不用的容器。如果你不用 Weaviate可以在docker-compose.yaml里把 weaviate 服务注释掉.env里VECTOR_STORE改成qdrant能省几百 MB。4.3 路径含中文或空格导致卷挂载失败现象docker compose up时报invalid mount path或容器启动后数据目录为空。原因Docker Desktop 在 Windows 上做路径转换时对中文和空格的处理不稳定。你把项目放在D:\我的项目\dify这种路径下就容易翻车。解决项目路径只用英文和数字比如D:\projects\dify。已经放错位置的docker compose down之后把整个目录移到纯英文路径再重新up -d。数据卷在 Docker 的虚拟磁盘里移动源码目录不影响已有数据但.env要跟着走。4.4 升级后数据库迁移失败现象git pull拉了新代码docker compose up -d之后 api 容器启动报alembic.util.exc.CommandError或数据库列不存在。原因Dify 版本升级时数据库 schema 会变需要跑迁移脚本。官方镜像在启动时会自动执行迁移但如果你的数据库卷是旧版本留下的且迁移脚本有冲突就会失败。解决升级前先备份数据库。执行docker compose exec db pg_dump -U postgres dify backup.sql把备份文件放到源码目录外。然后docker compose downgit pull再up -d。如果迁移还是失败看 api 日志里具体是哪条迁移报错有时候需要手动进数据库删掉冲突的记录。这个操作有风险新手建议直接备份后重建数据库卷代价是丢失已有应用数据。4.5 插件安装时 SSL 错误现象在 Dify 后台安装插件进度条卡住然后报SSLError或certificate verify failed。原因插件市场走 HTTPS容器内如果缺少 CA 证书或者系统时间不对就会校验失败。Windows 宿主机时间一般没问题但容器内时区可能是 UTC和证书有效期判断偶尔出偏差。解决先确认宿主机时间准确。然后在docker-compose.yaml的 api 服务里加环境变量TZAsia/Shanghai重启容器。如果还不行检查公司网络是否有证书拦截这种情况需要把自定义 CA 证书挂载进容器具体路径看你的网络环境。5. 进阶技巧用 Flask 写一个 Dify 工作流的外部调用壳5.1 为什么要自己包一层 FlaskDify 的工作流可以通过 API 对外暴露但它的 API 需要传Authorization: Bearer app-xxx这种应用级 Key而且请求体格式是固定的。如果你想让内部其他系统调用又不想把 Key 散落在各处常见做法是用 Flask 写一个薄薄的代理层对外暴露你自己的接口内部转发到 Dify顺便做鉴权、参数校验和日志。这个壳子还能解决一个实际问题Dify 工作流的输入变量如果很多调用方很容易传错。Flask 层可以做默认值填充和类型转换把 Dify 的报错挡在外面。5.2 Flask 代理的最小实现先装依赖pip install flask requests然后写一个app.pyfrom flask import Flask, request, jsonify import requests import os app Flask(__name__) # Dify 工作流的 API 地址和 Key从环境变量读不要硬编码 DIFY_API_BASE os.environ.get(DIFY_API_BASE, http://localhost:8080/v1) DIFY_API_KEY os.environ.get(DIFY_API_KEY, app-xxxxxxxx) app.route(/run-workflow, methods[POST]) def run_workflow(): # 接收调用方传来的 inputs做一层非空校验 data request.get_json() inputs data.get(inputs, {}) if not inputs: return jsonify({error: inputs is required}), 400 # 转发到 Dify 的 workflow run 接口 resp requests.post( f{DIFY_API_BASE}/workflows/run, headers{ Authorization: fBearer {DIFY_API_KEY}, Content-Type: application/json }, json{ inputs: inputs, response_mode: blocking, # blocking 表示同步等待结果 user: data.get(user, flask-proxy) }, timeout60 ) # 把 Dify 的响应原样返回调用方按需解析 return jsonify(resp.json()), resp.status_code if __name__ __main__: app.run(host0.0.0.0, port5000)这段代码的逻辑很直白Flask 收到请求后把inputs和user拿出来拼成 Dify 工作流 API 要求的格式带上 Key 转发过去。response_mode设成blocking表示同步等结果适合短流程如果工作流跑得久改成streaming然后做 SSE 转发但那样 Flask 这边要处理流式响应复杂度高一些。参数说明DIFY_API_BASE是你 Dify 的访问地址加/v1本地就是http://localhost:8080/v1。DIFY_API_KEY在 Dify 后台的应用「访问 API」页面生成每个应用一个。timeout60是防止 Dify 那边卡住导致 Flask 线程被占满按你工作流的最长耗时调整。5.3 验证与一个我常犯的错启动 Flask 后用 curl 测一下curl -X POST http://localhost:5000/run-workflow \ -H Content-Type: application/json \ -d {inputs: {query: 你好}, user: test}如果返回 Dify 工作流的执行结果说明代理通了。如果返回 401检查 Key 有没有复制错如果返回 404检查DIFY_API_BASE后面有没有多写或少写/v1。我自己的血泪经验是每次改完 Dify 的工作流输入变量忘了同步改 Flask 这边的默认值结果调用方传了旧字段名Dify 报变量不存在Flask 原样返回 400排查半天才发现是两边没对齐。从那以后我每次动工作流变量都强制走一遍「改 Dify → 改 Flask 默认值 → curl 测一遍」这个流程不再靠记忆。希望帮到你。本文还有配套的精品资源点击获取
返回列表