前几年大家谈智能助理,关注点大多还在“它能不能把话说顺”。到了现在,这个标准其实已经不够了。会解释、会总结、会改写,已经变成了多数系统都能做到的基础能力。真正把差距拉开的,往往不是它会不会回答,而是它能不能把问题继续往下处理。

真实业务里,很多问题天然横跨两类信息源:一边是文档、制度、说明、FAQ 这样的非结构化知识,另一边是订单、账户、交易、日志、报表这样的结构化数据。只要问题同时碰到这两边,系统就不能再只靠单一路径硬撑。

这篇文章想讨论的,就是这件事:当一个智能助理既要读文档,又要查数据库,它应该怎么设计,才不只是“会回答”,而是开始接近“能处理任务”。

如果要把结论先说在前面,我现在更相信这样一个判断:真正决定这类智能助理是否可用的,往往不是模型会不会答,而是系统能不能先把问题送进正确的处理链,再在链路出错时把它拉回来。

为什么不够用

如果只看演示,今天的智能助理已经很强了。它们能写摘要、能整理材料、能回答问题,甚至还能给出结构化输出。可一旦进入真实业务场景,问题很快就变得不一样了。

原因其实不复杂:业务里的信息从来不是放在同一个地方的。

规则、制度、产品说明、操作手册、经验总结,通常以文本形式存在,属于非结构化知识;客户、订单、账户、交易、库存、日志,则往往沉在数据库里,属于结构化数据。用户提问的时候不会主动替系统完成这层分类,他只会把问题直接抛过来。

这时候,一个系统如果只能做文档问答,它会说得头头是道,却不一定能给出真实数据;如果只能做数据库查询,它可能查到了结果,却不一定知道该怎么补足背景、解释字段,甚至不知道用户真正关心的是哪一层含义。

问题不在于 RAG 不够强,也不在于 Text-to-SQL 不够强,而在于很多真实问题天然横跨两类信息源。用户问的是一个问题,系统面对的却是两种完全不同的信息组织方式。

所以这里真正的难点,不是选哪种技术,而是系统在收到问题之后,能不能先判断应该去哪里取信息,再决定后续怎么处理。

很多系统不是输在回答,而是输在第一步就把问题送错了地方。

为什么要结合

RAG 的价值已经很明确了。它解决的是大模型知识更新滞后、事实不稳、容易幻觉的问题。系统先去知识库里检索相关内容,再把检索结果交给模型生成答案,这种方式很适合文档问答、制度说明、专业知识解释这类任务。

但它的边界也同样明确。RAG 更像是在“找资料 + 组织表达”,它擅长回答“怎么解释”,却不天然擅长回答“现在数据库里到底发生了什么”。如果用户的问题落到筛选、聚合、排序、统计这种结构化查询上,仅靠检索文本并不能真正解决问题。

Text-to-SQL 则正好相反。它的核心价值是把自然语言问题翻译成 SQL,让普通用户不用写查询语句,也能直接从数据库拿到结果。这类能力特别适合业务分析、明细筛选、统计汇总、报表查询。

但它也有自己的边界。数据库查出的结果并不自动等于“用户已经得到答案”。很多时候,系统还需要解释字段、补充规则背景、说明结果为什么重要,甚至把一堆结构化记录重新整理成自然语言。如果只有 Text-to-SQL,没有知识补充能力,系统很容易把答案交付在“查到了”这一步,却停在了“没讲明白”。

所以这两类能力都重要,但各自都不完整。

  • 只有 RAG,系统会解释,但不一定真能查到数据
  • 只有 Text-to-SQL,系统会查库,但不一定真能把结果讲清楚
  • 真正可用的智能助理,必须先知道当前问题更像哪一类任务,必要时还要让两条链路同时参与

我后来越来越不把这类系统理解成“更复杂的聊天机器人”,而是把它理解成:给智能助理补上一套问题分流和结果闭环能力。

先做分流

很多人一说系统架构,第一反应是模型、框架、前后端、服务编排。这些当然都重要,但真正做下来之后,我越来越觉得,这类系统里最关键的决策,不在“选了什么模型”,而在“用户的问题一进来,到底先送去哪里”。

所以这套系统的第一步不是立刻生成答案,而是先做问题理解和分流。实际实现时,可以先用意图分类把问题粗分成知识型、数据型和混合型,再结合置信度决定是单路执行,还是并行触发 RAG 和 SQL 查询。这样做的目的不是把分类做得多漂亮,而是尽量降低误路由的成本。

如果问题更偏知识型,比如某个制度怎么解释、某个业务流程是什么、某个概念在文档里如何定义,系统就优先走 RAG 路径:从知识库里检索相关片段,再结合用户问题交给模型生成答案。

如果问题更偏数据型,比如要统计某类记录、筛选某些对象、计算某个指标、对比某段时间内的变化,系统就走 Text-to-SQL 路径:把自然语言转成 SQL,在关系型数据库中执行,再把结果组织成自然语言输出。

如果问题同时依赖背景知识和具体数据,系统就不能只走一条路,而是要让知识检索和结构化查询都参与进来,最后再做结果融合。

举个更直观的例子。假设用户问:“上个月退款率为什么突然升高,是售后规则调整了,还是某类订单本身出了问题?”

这个问题如果只走 RAG,系统最多只能把售后政策变化、退款规则、历史说明文档找出来,但它不知道上个月究竟发生了什么;如果只走 Text-to-SQL,系统也许能把退款率、订单类型、时间分布查出来,但它未必知道规则变更发生在什么时候,更不知道该怎么解释规则变化与数据异常之间的关系。

只有把两条链路接起来,系统才有可能先去文档里找规则变化,再去数据库里查退款数据和订单结构,最后把两边的信息拼成一个用户真正能用的回答。

这也是我现在特别看重的一点:可用性的起点不是回答质量,而是路由正确率。

检索怎么做

做 RAG 时,一个很常见的直觉是:既然目标是语义检索,那直接上向量检索就可以了。它确实强,尤其是在用户提问和原文措辞不完全一致的时候,向量检索很适合靠语义相似性把相关内容找出来。

但真实场景里的检索问题没有这么干净。

因为业务知识里常常混着大量专业术语、固定表达、字段名、制度名、缩写词。对这类内容来说,“大概语义接近”并不总够用。有时用户只改了一个关键词,检索目标就已经完全不同;有时两个问题语义上很像,但真正决定答案的其实是某个专有名词、某个规则编号,或者某个字段约束。这个时候,如果系统只押注向量检索,结果并不会稳定。

所以我最后没有采用单一路径,而是做了一个双通道混合检索架构。

第一条通道是向量检索,负责抓语义相关性。系统把查询映射到语义空间里,再和文档向量做相似度匹配,这一部分适合处理“问法不同,但本质问题相近”的情况。

第二条通道是关键词检索,基于 BM25 做匹配。它的优势不在于理解语义,而在于对关键词、术语、实体词更敏感,尤其适合那些必须命中明确表达的场景。

两条通道并行完成检索后,系统再用 RRF,也就是递归排序融合算法,对结果做统一排序。这样做的关键,不只是把两个结果列表拼起来,而是让语义相似和精确匹配各自发挥作用,再通过排序融合减少单一检索方式的偏差。

为什么我更相信这类方案?因为它符合一个很现实的工程经验:很多系统失败,不是因为某个技术方向完全错了,而是因为它把某一种方法的长处误当成了通吃能力。

向量检索不是没用,它在语义匹配上非常重要;BM25 也不是“过时技术”,它在专业术语和固定表达上依然可靠。与其赌其中一种方式足够强,不如承认它们各有盲区,再让系统把这两个盲区尽量补上。

评估时,检索测试使用的是一个专业领域问答库,共 4999 条医疗相关问答对,涵盖常见疾病诊断、药物使用指南、治疗方案和健康建议等多个子领域,再从中随机抽取 1000 条样本做检索评估。这个设定的好处是,问题里既有专业术语,也有相对自然的问法,比较适合检验“语义相似”和“术语命中”之间的平衡。

实验结果也证明这个判断是成立的。混合检索在 k=1 时精确率达到 0.963,说明系统最前面的结果排序已经相当可靠;当 k=3 时召回率提升到 0.968,MRR 保持在 0.965 的高水平,意味着大多数相关信息在前三条结果里就能被覆盖,而且排位相当靠前。

这些数字如果只停留在评估表里,看起来只是几项性能指标;但放到真实交互里,它们对应的含义其实很直接:用户通常不会认真翻第十条结果,他能看到的主要就是前几条。系统不是“理论上能搜到”,而是要“很快把对的内容放到前面”。对交互型智能助理来说,后者才是真正影响体验的东西。

SQL 难在哪

如果说 RAG 里最容易被低估的是检索排序,那么 Text-to-SQL 里最容易被低估的,就是“生成成功”和“真正可用”之间那段距离。

从表面看,这个任务像是把自然语言翻译成 SQL。但只要接到真实数据库环境里,问题马上就会变得具体起来:字段名有没有用对,表之间的关联关系有没有处理清楚,筛选条件放得对不对,聚合逻辑有没有偏差,排序和分组是不是符合业务语义,最终生成的 SQL 到底能不能执行。

也就是说,Text-to-SQL 不是一个“看起来像 SQL”就算成功的任务,而是一个必须接受执行验证的任务。模型写出一句结构完整的查询,并不代表它真的查对了;有时语法能过,结果却错了;有时思路接近,但表名、字段、连接关系某个地方偏了一下,整个结果就全偏了。

这也是为什么我没有把 SQL 生成当成一个一次性动作,而是把它设计成一条可校验、可反馈、可修复的链路。

系统会先根据用户问题、数据库模式信息和提示词示例生成 SQL,然后做语法校验和执行验证。如果执行失败,系统不会直接把报错丢给用户,而是把原始 SQL、数据库返回的异常信息和当前数据库模式重新组织成新的提示,再调用模型执行修复。这个修复过程最多迭代三轮,直到生成合法 SQL 或达到上限为止。

这里还有一个容易被忽略的点:修复链路不能只是把报错再喂给模型一次,否则很容易越修越偏。真正有用的信息,是当前数据库 schema、出错 SQL、本轮报错原因,以及系统允许的查询边界。只有把这些约束一起放进去,修复过程才更像“带着护栏重试”,而不是盲目重写。

评估时,Text-to-SQL 测试集共 571 条案例,按复杂度分成 5 个等级。样本由自然语言问题、标准 SQL、期望结果集和难度标签组成。不同等级的划分,核心是在看查询是否涉及更复杂的筛选条件、多表连接、聚合统计和更强的业务语义约束。所有模型都在同一类数据库模式信息和相同评估口径下比较,尽量减少因为提示条件不同带来的干扰。

测试结果也说明了这一点。最终方案在高难度查询里的语法正确率达到 99.1%,结果匹配率达到 81.6%;而基准模型对应的语法正确率是 69.3%,结果匹配率只有 28.6%。

这个差距的意义,不只是“某个指标提高了几十个点”,而是说明在复杂查询场景里,系统已经从“经常查不出来、或者查得不可信”,跨到了“多数情况下能给出有效结果”的层级。

链路要闭合

如果只按实现清单来列,这个系统用了不少常见技术:Qwen2.5-32B、LoRA 微调、LangChain、FAISS、BM25、SQLite,也做了流式响应、异步通信和前后端页面实现。这些都是真实的工作量,但我越来越不想把重点放在“用了哪些组件”上。

因为一个系统用了什么,并不自动说明它为什么可用。

真正决定结果的,是这条链路有没有闭合。

  • 问题进来之后,系统能不能先判断该去知识库还是数据库
  • 知识检索时,系统能不能兼顾语义相关和术语命中
  • SQL 生成之后,系统能不能校验、执行、修复,而不是把错误原样暴露出来
  • 数据查出来以后,系统能不能重新解释成用户能理解的答案
  • 用户在前端交互时,系统有没有把等待状态、错误提示和结果反馈表达清楚

这些环节单拿出来看都不算特别“炫”,但少任何一个,整体体验都会明显下降。

所以如果一定要用一句话总结我对这类系统最大的认识,我现在更愿意这样说:模型决定上限,系统设计决定下限,而用户真正先感受到的,通常是那个下限。

模型能力很强,但检索不准、路由出错、SQL 报错后没有恢复机制,用户感受到的依然是不稳定。反过来,即便模型不是最顶级,只要检索、分流、校验、反馈和解释这些环节设计得足够扎实,系统表现出来的完成度也会远高于“只看参数规模”的预期。

结果说明什么

最后再回头看测试结果,其实更重要的不是“成绩好不好看”,而是这些数字到底说明了什么。

真正值得关注的,不是简单任务上的得分,而是系统在复杂场景里有没有明显崩掉。因为简单场景里,很多模型都能表现得还不错,真正拉开差距的是多表连接、复杂条件、聚合统计、业务语义更强的部分。

最终方案在高难度 Text-to-SQL 任务上仍然能保持 99.1% 的语法正确率和 81.6% 的结果匹配率,这说明它的价值不只是“平均分更高”,而是把复杂场景下的可用性也拉上来了。

RAG 这边也一样。k=1 时精确率达到 0.963,k=3 时召回率达到 0.968,MRR 达到 0.965。对实际系统来说,这意味着它不是“搜到了相关内容”就算完,而是大概率能在前几条结果里把最有用的内容放到用户面前。

前端测试的数据相对没那么“学术化”,但也不能忽略。页面跳转成功率达到 100%,核心功能完成率维持在 97% 以上,至少说明这个项目不是只停留在离线实验或单模块 Demo,而是把完整交互链路也真正搭起来了。

这些结果当然不意味着问题已经被彻底解决,但至少说明一件事:把 RAG、Text-to-SQL、问题分流、检索排序、错误修复和结果解释串成一条完整链路,确实比单一路径更接近真实可用的智能助理。

我的判断

最开始看这类问题时,我更容易把它理解成“把几种能力接起来,做一个更强的助理”。但真正把系统做完之后,我的理解反而变得更具体,也更现实了。

第一,真正有用的智能助理,迟早都要接外部系统。

如果一个系统只能基于参数知识回答问题,那它再会说,也更像一个很强的聊天工具。一旦进入业务场景,它就必须开始接知识库、接数据库、接规则系统,甚至接后续执行流程。只有这样,它才不是“在对话框里表现不错”,而是真正开始承担信息处理任务。

第二,系统可靠性不是从单一模型能力里自然长出来的。

用户通常不会关心你用的是哪个模型、多少参数、有没有做微调。他真正感受到的是另一套东西:检索准不准,查库能不能成功,报错后会不会卡死,结果好不好理解,界面有没有反馈。这些体验背后对应的不是某一个超级模型,而是一整条工程链路是否足够稳。

第三,未来这类系统的竞争,很大一部分会转到“怎么接系统”上。

至少在我现在的理解里,真正拉开差距的部分,很可能会越来越集中在这些问题上:谁更会接知识,谁更会接数据,谁更能处理复杂任务的路由和纠错,谁更能把最后的结果交付成用户真正能用的答案。模型当然仍然重要,但如果没有外围系统把它支撑起来,它的能力很难完整落到现实任务里。

如果把这三点再压缩一下,其实就是一句话:智能助理从“会回答”走向“能处理任务”,中间差的不是一点提示词技巧,而是一套能接知识、接数据、接错误恢复的系统能力。

收个尾

把 RAG 和 Text-to-SQL 接到同一个智能助理里,看上去像是在做一次技术叠加,但我现在更愿意把它理解成一次能力边界的推进。

RAG 让系统不再只依赖模型内部的参数知识,Text-to-SQL 让系统开始真正触碰结构化数据,而当这两条能力链被放进同一个问题处理流程里,智能助理才第一次有机会从“会回答”走向“会查、会解释、会处理任务”。

这一步并不意味着问题已经解决了。知识库自动更新、多轮上下文追踪、更复杂业务场景下的路由策略、多模态输入、低延迟与高准确率之间的平衡,这些都还是后续继续推进的方向。

但至少对我来说,这类系统让我更清楚地看到了一点:如果智能助理想真正进入复杂信息环境,它缺的从来不只是更大的模型,而是把知识、数据和任务链路接起来的系统能力。