Skip to content

AI 查询 ERP 数据库时,为什么不该默认让模型写 SQL

很多 AI + 数据库 demo 都从同一条捷径开始:

  1. 连接一个大模型。
  2. 把数据库 schema 给它。
  3. 让模型生成 SQL。
  4. 执行 SQL。
  5. 把结果总结成一段话或一张图。

如果只是演示一个玩具数据库,这条路径没问题。它直观、快,也容易让人看到“自然语言问数”的效果。

但如果目标是 ERP、CRM、财务、库存、人事这类业务系统,这不应该是默认架构。

原因不是模型一定写不好 SQL。真正的问题是:ERP 数据库里的安全边界、业务语义、公司隔离、字段可见性和审计要求,通常并不完整地存在于物理表结构里。让模型直接看 schema 并生成 SQL,很容易把“能查到数据”误认为“应该允许这样查”。

生产系统里更应该问的问题不是:

text
模型能不能生成 SQL?

而是:

text
系统能不能在保留 ERP 原有治理规则的前提下回答业务问题?

这两个问题的工程含义完全不同。

裸 SQL 会跳过太多业务边界

ERP 数据不是普通的表和字段。

一个订单表里不仅有金额、客户和状态,还隐含着销售组织、公司范围、审批状态、会计口径、实施商自定义字段、用户权限和审计要求。一个字段叫 state,在不同模型里可能表示销售订单状态、发票状态、库存调拨状态、审批状态,也可能是本地二开后的业务状态。

数据库 schema 能告诉模型字段名和类型,但它很难告诉模型:

  • 当前用户能看哪些业务对象;
  • 哪些记录规则应该生效;
  • 当前用户属于哪些公司;
  • 哪些字段对当前角色不可见;
  • 某个金额字段应该按什么业务口径解释;
  • 某个查询是否应该被拒绝,而不是让模型猜一个答案。

这就是 raw SQL 作为默认接口的问题。

第一,权限通常不在 schema 里。表名、列名、外键关系不会自动表达“这个用户只能看自己公司”“这个销售只能看自己的客户”“这个字段对普通员工不可见”。

第二,业务语义不能靠字段名猜。模型可能猜对一部分字段,但猜对不是治理。生产系统需要可解释、可复查、可维护的口径。

第三,审计链路会变弱。如果最终只留下一个模型生成的 SQL 字符串,系统还要额外解释:为什么这条查询被允许?它映射到哪个业务模型?应用了哪些权限规则?返回结果是否在用户权限范围内?

第四,能力边界会不断膨胀。一旦系统接受任意 SQL,用户自然会继续要求 join、子查询、窗口函数、CTE、临时字段、“再加一列”。能力看起来变强了,但安全边界会越来越模糊。

所以,问题不是 SQL 本身有罪。问题是把“模型生成 raw SQL”当成 ERP AI 的默认接口。

raw schema 不是业务授权模型

很多 AI 数据查询方案会先做 schema introspection:扫描表、字段、关系,然后把这些信息交给模型。

这对开发辅助、探索环境、临时分析有价值。但它不等于业务授权模型。

业务授权模型至少要回答几类问题:

  • 用户是谁:自然人、服务账号,还是某个租户下的应用身份;
  • 用户能看什么:业务对象、记录范围、公司范围、字段范围;
  • 用户能怎么查:明细、聚合、导出、跨模型分析是否允许;
  • 指标是什么意思:销售额、应收、库存、采购额分别用哪些字段和状态计算;
  • 结果如何复查:查询过程、权限边界、数据来源是否可审计。

这些内容很少能从裸表结构里可靠推导出来。

对 ERP 来说,更合适的接口不是“这里有数据库,你写 SQL 吧”,而是“这里有一组经过治理的业务查询模型,你可以在这些边界内提问”。

更稳的默认路线:语义模型和查询模型

语义层的价值,不是给 AI 更多自由,而是把自由限制在可维护的业务边界内。

一个面向 AI 查询的语义模型或查询模型,应该明确描述:

  • 业务字段的含义;
  • 可用维度和指标;
  • 支持哪些过滤、排序和聚合;
  • 哪些关系是允许使用的;
  • 指标计算口径;
  • 权限和字段边界;
  • 查询能力范围;
  • 什么时候需要澄清;
  • 什么时候必须拒绝。

这样模型面对的就不是数据库内部结构,而是受控的业务接口。

例如用户问:

text
统计最近 30 天销售额最高的 5 个客户。

更合理的执行路径应该是:

  1. 识别这是销售分析问题。
  2. 选择受治理的销售查询模型。
  3. 确认时间范围、指标口径和聚合粒度。
  4. 绑定当前有效用户。
  5. 在查询执行前应用用户权限、记录规则和公司边界。
  6. 只返回允许范围内的结构化结果。
  7. 保留查询模型、过滤条件、行数、执行证据和审计信息。

这里可以有 SQL 参与执行,但 SQL 不应该是模型面对用户时的主要接口,更不应该是绕开 ERP 权限体系的捷径。

MCP 解决 transport,不自动解决治理

MCP 给 AI client 调用工具提供了统一方式,这是有价值的。

但 MCP 本身并不会保证工具安全。

一个 MCP tool 可以暴露 raw SQL。也可以直接返回敏感字段。可以忽略业务系统权限。也可以把内部错误、堆栈、表结构泄露给调用方。

所以企业数据访问里,关键不只是“有没有 MCP”,而是 MCP tool 的边界怎么设计。

一个生产可接受的业务数据工具,至少应该在服务器端处理:

  • authentication 和 tenant context;
  • effective user 或 service principal 绑定;
  • 宿主系统权限投影;
  • 可见 query model 选择;
  • 查询参数校验;
  • 结果裁剪和脱敏;
  • audit evidence;
  • scope 不清楚时 fail closed。

换句话说,MCP 是 transport。真正的安全边界在 governed tool design。

Odoo 是一个很具体的例子

Odoo 很适合说明这个问题。

Odoo 用户不是 PostgreSQL 用户。Odoo 的权限控制在应用层,包括:

  • ir.model.access:模型级访问权限;
  • ir.rule:记录规则;
  • multi-company:多公司边界;
  • field visibility:字段可见性;
  • 各模块自己的业务状态和工作流约束。

如果 AI 工具绕过 Odoo,直接连 PostgreSQL 查询,就可能绕过管理员真正配置和维护的权限体系。

更合理的做法是让 Odoo 继续作为权限和业务上下文的权威来源:

  • MCP client 通过 Odoo 侧签发或管理的访问方式接入;
  • 当前有效 Odoo 用户决定可见查询模型;
  • ir.model.accessir.rule 在查询执行前参与;
  • 多公司边界在查询条件里保留;
  • 字段边界在结果返回给 AI 前处理;
  • 管理员可以复查查询过程和结果范围。

这里的重点不是 Odoo 独有。Odoo 只是把 ERP 权限问题展示得足够清楚。其他业务系统同样需要类似的宿主权限投影和受控查询边界。

生产级 AI 查询要有澄清和拒绝

很多 demo 希望模型“什么都能答”。生产系统恰好相反:它必须知道什么时候不能答。

当用户没有给时间范围、指标口径、业务粒度时,系统应该澄清。例如:

text
你说的销售额是确认订单金额,还是已开票金额?

当用户请求物理表访问、权限绕过、敏感字段、写回业务数据、预测或因果判断时,系统应该拒绝或转人工流程。例如:

text
这个请求需要访问物理表或超出当前用户权限范围,无法执行。

澄清和拒绝不是体验缺陷,而是生产治理能力的一部分。

一个严肃的 AI 查询系统,不应该把所有问题都硬转成 SQL。它应该清楚地区分:

  • 可以直接执行的标准查询;
  • 需要补充业务口径的问题;
  • 需要管理员授权或另走流程的问题;
  • 应该拒绝的问题。

能力应该分层,而不是承诺任意 SQL

“支持任意 SQL”听起来强,但在企业业务数据里不是最值得追求的承诺。

更实际的做法是按问题类型分层:

  • 标准 DSL:明细、过滤、聚合、TopN、趋势。
  • 受控表达式查询:字段比较、日期差、范围校验、审计规则。
  • 分阶段查询:占比、累计贡献、SLA、漏斗、窗口类模式。
  • 小结果集二次分析:在已授权、已限制的数据集上做进一步整理。
  • CLARIFY:缺少时间范围、指标定义、粒度或业务规则时先澄清。
  • REJECT:请求预测、因果、物理表访问、权限绕过或写回业务数据时拒绝。

这比“模型可以写任何 SQL”更诚实,也更容易维护。

一个更安全的默认原则

如果要把 AI 接入 ERP 数据,建议把默认原则改成下面几条:

  1. 不把 unrestricted database schema 暴露给模型作为主要接口。
  2. 不让 model-generated SQL 成为生产查询的默认路径。
  3. 暴露受治理的 semantic query tools。
  4. 在执行前绑定 effective user,并投影宿主系统权限。
  5. 返回结构化结果,同时保留 audit 和 provenance。
  6. 边界不清楚时澄清;越界时拒绝。
  7. 不承诺任意 SQL、业务写回、权限绕过、预测或因果判断。

这条路线没有 raw SQL demo 那么炫,但更接近企业系统真正需要的东西:可解释、可审计、可维护,并且不破坏原有权限体系。

Foggy Odoo Bridge / Foggy Data MCP 目前走的也是这个方向:通过 Odoo Bridge、语义查询模型和 MCP 工具边界,让 AI client 查询 Odoo 业务数据时,仍然由 Odoo 权限控制可见范围。Community 更适合轻量评估和自托管实验,Pro 则面向 Odoo 侧完整采用、内置 AI Chat、模型治理、审计和支持。

这不是“让 AI 直接查数据库”的故事。更准确地说,是把 AI 数据访问放回业务系统应有的治理边界里。

继续阅读