同一笔业务销售台账里是一个金额财务账里是另一个金额银行流水里又是第三个数字。三方各查各自的系统结论都不算错但合不到一起。这不是谁录错了的 bug而是数据口径从一开始就不是同一个事实源推导出来的。本文把这个问题还原成工程问题给出一种分层做法并说明其中的取舍与边界。文中场景为示意用于说明一类工程问题不指向任何具体企业。一、问题还原同一事实的多源重建先把现象抽象一下。设一笔业务为E它会在多个位置产生各自的投影业务侧投影E.biz签约金额、跟进状态落在聊天记录、表格或业务系统交付侧投影E.deliver里程碑、验收状态落在项目群、文档资金侧投影E.cash到账事实落在银行流水会计侧投影E.gl入账结果落在凭证明细。问题不在某个投影错了而在于E这个事实本体从未被显式建模。各投影独立产生、独立演进、口径各自定义等到需要聚合时只能靠人工 re-key人对人、表对表去对齐。这就是对不上的根因——一致性靠事后对账维持而不是在发生时就由结构定下来。工程上常见的两个误区加人手或加频次把人工对齐从月底一次改成每天一次。这只降低了 latency没有降低 error 概率对齐动作本身仍是有损的。事后 ETL 汇聚抽多源数据进数仓做宽表。若源头的口径本身不一致宽表只是把不一致做了个好看的展示层聚合后仍然要人工仲裁以谁为准。两者的共同前提都是聚合不够快而真实瓶颈是事实没有在单一处成型。二、约束条件这类系统的目标环境中小规模企业有几个硬约束直接决定方案不能照搬大厂数仓那套无专职信息化团队方案必须能由业务/财务角色自行配置运维面要小。业务入口在 IM日常发生在飞书、企业微信里不能要求全员改用一个新客户端。财务人手有限要减少收集与搬运而不是新增一个填表进系统的环节。人机责任边界清晰记账判断、付款、入账、结账、申报必须由责任人完成系统不能越界代做。三、分层方案采用接入层 — 应用层 — 智能层 — 数据层四层结构各层职责独立、可独立扩展┌───────────────────────────────────────────────┐ │ 接入层飞书应用 / 企业微信应用 / Web 工作台 │ │ 统一身份认证 请求分发 │ └───────────────────────┬───────────────────────┘ │ 同一套接口按角色渲染 ┌───────────────────────▼───────────────────────┐ │ 应用层客户销售 / 合同履约 / 项目交付 / │ │ 费用报销 / 人事薪酬 / 资金账务 流程引擎 │ │ 权限引擎 经营分析 │ └───────────────────────┬───────────────────────┘ │ 业务规则 / 流转 / 权限判定 ┌───────────────────────▼───────────────────────┐ │ 智能层意图识别 / 票据识别 / 合同要素抽取 / │ │ 流水匹配 / 经营摘要生成 模型路由 │ └───────────────────────┬───────────────────────┘ │ 结构化事实 可读结论 ┌───────────────────────▼───────────────────────┐ │ 数据层业务库 / 凭证账簿 / 文件影像 / 缓存/日志│ └───────────────────────────────────────────────┘三端共用同一套接口服务端按角色渲染不同视图因此飞书、企业微信和 Web 工作台拿到的是同一笔业务、同一笔钱、同一份结果。这一层的价值是把多源收敛为单源、多视图——入口多但事实只有一份。四、关键取舍方案能不能落地取决于三个取舍。取舍一不做事后汇聚做发生即结构化。事后 ETL 需要假设源数据是对齐的而本问题恰恰是源数据不对齐。因此把结构化时机前移到业务发生那一刻员工在 IM 里提交时系统即时抽取并落成有结构的记录。代价是链路更长、要处理自然语言输入收益是从根上消除二次对账。这里选择承担前者的复杂度。取舍二AI 只做抽取不做判定。智能层负责听懂、看懂、整理意图识别、票据识别、合同要素抽取、流水匹配、摘要生成但不产出任何记账结论。所有需要担责的动作路由到人。这样做的原因有二一是责任可归属——出现争议时能追到人二是可降级——模型繁忙或不可用时规则、模板和工作台照常办事业务不中断。取舍三状态显式建模不做已完成这种模糊态。一笔钱要区分计划 / 到账 / 入账三段状态而不是合并成一个布尔值。否则合同生效会被误读成钱已到账。多一个维度的复杂度换来的是不会在关键判断上撒谎。五、落地要点数据层用一个轻量的事实载体表达业务对象 状态 证据示意如下字段为设计示意的简化版BusinessFact id string 主键 object_type enum 客户/合同/项目/票据/凭证 amount decimal 金额 state enum plan | arrive | posted -- 计划/到账/入账 evidence_ref string 指向票据影像/流水的引用 owner_id string 责任人 occurred_at timestamp 事实发生时间 created_at timestamp一笔业务在系统内走六个环节其中前两步在业务侧、后两步在财务侧、中间两步是系统的承接动作序号环节处理1发起员工在 IM 或工作台提交系统识别意图并补齐缺失信息2确认员工核对系统生成的摘要确认后正式提交3审批按企业自定义流程按岗位与金额等条件分支4执行需收付的事项进入财务处理核对流水与回单5入账生成凭证草稿经复核后过账6呈现账簿、报表、经营摘要更新责任人收到结果或提醒伪代码上入口是一个常规的识别—追问—确认三步流程def submit(user, text, attachments): intent recognize_intent(text) # 智能层听懂要办什么 facts extract(intent, attachments) # 票据识别 / 要素抽取 missing diff(required(intent), facts) # 只追问还缺的那一项 if missing: return ask(user, missing) # 不阻断补完继续 summary build_summary(intent, facts) return confirm(user, summary) # 人确认后才进入正式流程 def on_confirmed(fact): route_to_approval(fact) # 应用层按权限与规则流转 # 付款 / 入账 / 结账 由责任人在应用层执行智能层不产出结论关键点是confirm之后才产生正式事实上传发票只是把证据放进这件事正式凭证是财务复核之后的结果两者不在同一步完成。六、系统边界这一节是给技术选型方的提醒避免把系统能力想大智能层不承担记账判断与责任凭证复核、过账、结账由企业责任人执行法定申报的提交动作不由系统完成系统提供材料与辅助文件经营决策、员工薪酬决定不在系统职责内模型不可用时可降级业务不中断——这是取舍二的直接收益。把边界写进设计而不是写进免责声明系统才经得起长期使用。从工程视角看边界清晰还有一个副作用它让系统的可测范围变清楚了。哪些环节应当拿到确定结果抽取结果、流水是否命中、凭证草稿是否生成哪些环节必须保留人工确认过账、结账、申报在测试和验收里对应的是两类完全不同的指标。混在一起度量最后会把责任也测糊。附注上文的场景为工程示意不含任何真实客户数据也不引用任何客户案例。文中所述的四层结构、六个环节与人机边界参考自一个经营协同项目的公开技术口径。接入方式、部署形态、权限与审计范围这块评论区可以交流你们实际的做法。