Dify与RAGFlow的混合架构:如何实现1+1>2的知识库管理效果
企业在搭建RAG知识库时,Dify和RAGFlow这两个开源框架该怎么选?这个问题几乎每个做RAG落地的团队都会遇到。从实际项目经验来看,处理特别复杂的文档和非结构化数据时,RAGFlow是更合适的选择;而如果场景需要多模型协作和复杂的业务流程,Dify则更具优势。
但答案或许出乎你的预料:这并不是一个非此即彼的选择。
这篇内容要讲清楚的是一个更优的方案——把Dify作为主框架,利用其Agent和工作流组件构建应用层,同时通过API调用RAGFlow的知识库模块。这样既能享受Dify友好的界面和工作流能力,又能获得RAGFlow在深度文档处理上的优势。
需要说明的是,除了Dify+RAGFlow的组合,也可以根据具体业务场景加入其他开源框架,比如LlamaIndex、LightRAG等。
以下进入正题。
从优势互补说起
Dify的主要优势
易用性高,上手快,基本不用花太长时间阅读文档就能跑起来。部署速度也足够打动人——30分钟就能起一个可用原型。模块化设计让二次开发变得顺手,同时支持丰富的外部拓展工具和任务流编排,整体感觉类似Coze,但可扩展性更好。一个很关键的点是,Dify支持跨知识库检索,能自动匹配合适的知识库,这一点RAGFlow目前还做不到。
RAGFlow的主要优势
文件精细解析能力是它的看家本领,特别是那些让人头疼的PDF、扫描件、表格等复杂文档,处理起来很有一套。背后的DeepDoc技术专门应对非结构化文档,再加上OCR支持和内置的多种文档切分模板,从文档处理角度看几乎是首选。另外,在延迟敏感的应用场景中表现也不错,能撑起较重的工作负载。
优势互补的好处
把两者的优势捏到一起,能实现几个很实在的目标:利用Dify强大的工作流编排和Agent能力构建复杂应用,同时获得RAGFlow优秀的文档处理和解析能力;通过API集成,系统的灵活性和可扩展性也能得到保障。
端口修改的准备工作
端口概念解析
先简单说一下Docker Compose中的端口映射逻辑。格式是A:B,其中A是宿主机端口,B是容器内部端口。比如80:80,意思就是宿主机的80端口映射到容器的80端口;443:443同理。容器内80端口一般处理HTTP请求,443处理HTTPS请求。
端口修改
RAGFlow和Dify官方都推荐用Docker部署。为了防止端口冲突,一个稳妥的做法是把RAGFlow的宿主机端口改成别的值,但保留容器端口不变。比如80:80改成8080:80,443:443改成8443:443。
改的时候注意,修改的是左边的数字(宿主机端口),但要确保新端口没有被其他程序占用。改完后记得保存docker-compose.yml文件,然后重启容器让新配置生效。通常用docker-compose down和docker-compose up -d重新启动服务。
这样做的好处是,同时部署RAGFlow和Dify时不会出现宿主机端口冲突,内部服务依然使用原有的HTTP/HTTPS端口设置。
有朋友可能会问,RAGFlow和Dify都有Redis服务,是否需要改RAGFlow的Redis端口?答案是不需要。Dify的Redis仅在内部使用,它的Redis容器没有把服务端口映射到宿主机,所以只供容器间访问,不会跟外部产生冲突。
Dify启动命令修改
Docker Compose用项目名称来隔离不同的项目环境。默认情况下,项目名称就是docker-compose.yml所在目录的名称。问题就出在这里——RAGFlow和Dify的docker-compose.yml都放在docker目录下,导致两个服务的容器没有被有效隔离,从而引发冲突。
解决办法其实很简单:RAGFlow的Docker服务启动方式不变,但Dify启动时需要通过-p参数显式指定项目名称。比如docker compose -p dify_docker up -d。
修改验证
在浏览器访问http://localhost:8080,看看RAGFlow是否正常运行。如果服务正常启动,应该能看到RAGFlow的Web界面。完成这些步骤后,RAGFlow的默认端口就从80改成了8080。
这里需要注意一个细节:之前介绍的在RAGFlow中通过图片服务器容器化实现图片问答的脚本,因为改动了端口号,所以需要修改ragflow_build.py中初始化RAGFlow客户端的代码。默认base_url参数是"http://localhost",没有指定端口号。既然已经把80端口映射改成了8080:80,base_url参数也需要相应更新。

详细操作步骤
URL配置注意
在Dify中配置RAGFlow的知识库时,需要在RAGFlow的基础Base URL后面加上"api/v1/dify"。这是Dify特定的API路径,负责版本控制和模块划分,也符合RESTful的设计思想。
创建知识库
完成Dify和RAGFlow的API连接后,接下来就是创建知识库。需要注意,这个时候要点的是"连接外部知识库"这个按钮,而不是直接创建新的。下一步会要求输入外部知识库ID,这个信息在RAGFlow对应的知识库页面,浏览器地址后缀上能看到完整的ID数字,直接复制过来填上就行。
连通测试
创建完知识库后,可以对知识库进行召回测试。这个功能类似RAGFlow的检索测试,主要用来验证上面的两步配置是否成功。值得一说的是,这一步还不需要配置LLM就可以直接测试。
模型供应商配置
在创建具体的ChatBot之前,需要先在设置页面配置LLM的来源。既可以用Ollama部署本地模型,也可以直接选择商业API。
一个实用的建议是:为了后续能更好地做分块和检索策略的调优,如果电脑上没有部署DeepSeek-R1-Distill-Qwen-32B或同等水平的开源模型,这一步还是先用商业API更稳妥。
创建ChatBot
这一步很简单:输入系统提示词,绑定上面创建的知识库,然后在右上角选择要用的模型,就可以开始问答测试了。为了测试效果,这里输入的提示词和RAGFlow中的保持一致,大家可以做个参考。就ChatBot功能来说,初步测试下来准确率没有明显差别,图片也能正常显示。
不过Dify中的ChatBot提供了更丰富的配置选项。比如为了测试不同问答模型的效果,可以同时添加多个LLM对同一个问题进行对比回答。这个入口稍微有点深,可以参考图示操作。
测试用的是DeepSeek-R1-Distill-Qwen-32B和Qwen2.5-32B-Instruct两个模型,试了几个问题,回答速度和效果基本没有明显差别,都还够用。
为什么选这两个开源模型?虽然并不建议中小企业在POC阶段过早做LLM的本地化部署,但真要部署这个尺寸的开源模型也基本够用了。所以日常给企业做项目Demo时,也会倾向于直接用这两个来测试,确保实际本地部署后的效果一致性。
另外,这个ChatBot还有一个特点:可以根据业务需求增加更多个性化功能,比如Conversation Opener、Follow-up、Text to Speech、Speech to Text等,具体可以自己测试。需要说明的是,Citations and Attributions(回答的出处引用)是默认打开的。
创建工作流
Dify中Studio模块提供了Chatbot、Agent、Completion、Chatflow、Workflow等多种选择,工作流里又包含了很多Blocks和Tools,看起来确实有点眼花缭乱。
应用类型比较
Chatbot:基础聊天助手,适合简单的问答交互。
Chatflow:面向对话类场景,支持多步逻辑和对话历史记忆,适合客服、语义搜索等场景。
Workflow:面向自动化和批处理场景,适合高质量翻译、数据分析、内容生成、邮件自动化等。
Agent:智能助手,能自主规划、拆解、调用工具和迭代复杂任务。
Chatflow相比Workflow增加了对话特性支持,比如对话历史记忆、标注回复和Answer节点。Workflow则专注于复杂业务逻辑处理,提供丰富逻辑节点和定时/事件触发能力。
功能块(Block)解析
LLM:核心处理节点,用大语言模型处理各类任务。
Knowledge Retrieval:从知识库检索相关内容。
Answer:定义回复内容的格式和展示。
Agent:智能助手节点,可自主规划执行任务。
Question Understand:理解用户意图。
Question Classifier:对问题进行分类,引导不同处理逻辑。
IF/ELSE:条件分支节点,基于条件分流。
Iteration/Loop:循环处理节点。
Code:执行自定义代码逻辑。
Template:用Jinja2模板进行数据转换。
Variable Aggregator:聚合多分支变量。
Parameter Extractor:从自然语言提取结构化参数。
工具(Tool)组件解析
第一方工具:Dify生态内建的工具,比如Audio、Code Interpreter、CurrentTime、WebScraper等。
自定义工具:可以导入符合OpenAPI/Swagger或OpenAI Plugin规范的API工具。
这些工具能扩展LLM的能力,实现联网搜索、科学计算、绘图等,让AI应用连接外部世界。通过自定义工具,还能做内容审查、敏感词过滤等。自定义工具这个功能确实很强,后续可以考虑专门出一期来介绍。
工作流应用示例
泵是工厂常见的通用设备,一旦突发故障,整条生产线都可能停摆,造成重大经济损失。下面是一个近期实施过的泵类设备预测性维护智能系统案例,充分利用了Dify的各种功能模块和工具节点,整合了静态知识库、MCP链接外部数据源、问答分类和维保报告生成。
系统架构图
+----------------------------------+
| 用户界面层 |
| Web界面 | 移动App | 企业微信集成 |
+----------------------------------+
|
+----------------------------------+
| Dify核心平台层 |
| 工作流编排 | Agent | RAG | 知识库 |
+----------------------------------+
| |
+----------------+ +------------------+
| MCP连接层 | | 外部系统集成 |
| 数据收集接口 | | ERP | MES | CMMS |
+----------------+ +------------------+
|
+----------------------------------+
| 设备物联网层 |
| 振动传感器 | 温度传感器 | 压力传感器 |
+----------------------------------+
工作流程设计
A. 状态监控工作流
通过传感器持续监控泵的振动、温度、压力等参数,用IF/ELSE节点对异常状态进行判断,发现异常时触发告警。
B. 故障预测工作流
将收集的数据与历史故障模式进行比对,用LLM和Knowledge Retrieval节点分析数据趋势,预测可能的故障时间和类型。
C. 维保建议工作流
根据预测结果生成具体的维护建议和计划,包括所需备件、维修时长和最佳维修时间窗口,通过Template节点生成标准化工单。
D. 闭环反馈工作流
收集实际维修结果与预测的对比,通过Agent节点分析差异并不断优化模型,形成闭环反馈,持续提升预测准确性。
关键节点配置示例
设备状态监控节点配置:
- HTTP Request节点:
接口URL: http://iot-platform/api/pump/status
参数: {"pumpId": "{{pumpId}}", "timeRange": "{{timeRange}}"}
- Code节点(数据处理):
处理振动、温度等数据,计算偏差值
- IF/ELSE节点:
条件: vibration > threshold || temperature > limit
是分支: 触发告警流程
否分支: 正常记录数据
故障预测LLM节点提示词:
系统提示: 你是一位专业的泵类设备故障预测专家。根据以下设备参数和历史数据,分析可能存在的故障风险,预测故障类型和可能的发生时间。
用户输入:
设备ID: {{pumpId}}
当前振动值: {{vibration}}
当前温度: {{temperature}}
当前压力: {{pressure}}
历史故障模式: {{historyFailures}}
维保报告生成节点:
- Template节点:
设备巡检报告
设备ID: {{pumpId}}
巡检时间: {{inspectionTime}}
设备状态: {{status}}
预测寿命: {{remainingLife}}
异常项:
{% for issue in issues %}
- {{issue.name}}: {{issue.description}}
{% endfor %}
维护建议:
{{maintenanceSuggestions}}
下次计划维护时间: {{nextMaintenanceDate}}
写在最后
RAG从2020年由Meta提出,到2023年春季Nvidia GTC大会后开始火热,期间一直面临着来自"微调"和"长上下文LLM"的对比争议。但两年下来,行业共识已经基本形成:
一方面,从成本和实时性角度,RAG具有压倒性优势,而效果上与微调相差并不大;即使需要微调介入的场景,RAG通常也是不可或缺的。另一方面,长上下文LLM依然面临上下文段落增加时准确率不断下降的事实。因此,在任何情况下,提供高精度的搜索系统(RAG)都是极有价值的。RAG目前已经成了一种事实上的落地标准架构。
RAG技术正处于快速发展期,各垂直场景的最佳实践仍在探索之中。
