Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
23 commits
Select commit Hold shift + click to select a range
ae0d886
Merge branch 'feat/dimensions'
Apr 11, 2026
5547328
refactor: remove LLM dependency from fallback and leverage host agent…
Apr 11, 2026
640edea
fix(query): union journal and balance_sheet for available accounts hint
Apr 11, 2026
231b9da
refactor(query): extract balance and period flows in queryPrecise
Apr 11, 2026
fe1f6dd
feat(db,query): add CAS mapping and return AR/AP detail top rankings
Apr 11, 2026
dec0157
feat: 完善穿透审计核心算法,支持 Max-Abs 流转计算与年度回溯自愈业务逻辑逻辑加固核对示范)
Apr 11, 2026
ce10361
feat: 升级实体识别引擎 V8,优化精准对账拦截与数据库优先的实体扫描逻辑业务逻辑逻辑加固核对示范)
Apr 11, 2026
f614c42
feat: 优化数据库 Schema 索引,完善实物资产与财务流水平滑同步管道业务逻辑逻辑加固核对示范)
Apr 11, 2026
2ebbffd
test/chore: 对齐全量集成测试套件,删除 llm_fallback 等冗余逻辑,完成代码库瘦身业务逻辑逻辑加固核对示范)
Apr 11, 2026
c31ea71
fix: align accounting calculations and hierarchy seeding for test sta…
Apr 12, 2026
b1017a6
docs: add finance calculation logic meeting summary
Apr 12, 2026
8c5e8b3
feat: add host LLM payload interface and dual-perspective core metric…
Apr 12, 2026
bd39ec2
chore: ignore temporary scratch artifacts
Apr 12, 2026
11e1ed7
feat: 更新插件描述和功能文档,增强对接 OpenClaw 的接口说明
Apr 12, 2026
cd2ffca
docs: add CLAUDE.md boss assistant defaults
Apr 12, 2026
7b8cf7f
feat: 添加财务统计基本原则,明确查询时的错误示例与正确做法
Apr 12, 2026
6a27584
fix(query): repair finance routing, dual-metric output, and strict re…
Apr 13, 2026
5f72cbf
docs(config): add dated repair plan, architecture views, rules.json, …
Apr 13, 2026
a1a5e29
docs(skill): rename skill name to finance and move version into descr…
Apr 13, 2026
017c387
feat(ingest): support merged financial report import with dual-sheet …
Apr 14, 2026
9c560b9
feat(query): externalize high-frequency intent rules and strengthen c…
Apr 14, 2026
8d73151
docs(testing): update skill/readme and make prod audit regression aut…
Apr 14, 2026
fc5a131
test(integration): add finance schema contract checks
Apr 14, 2026
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 6 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,10 @@ financeqa
# Database
*.db
*.db-*
*.db.bak*
*.bak.db
*.bak.sqlite
*.sqlite.bak*

# OS
.DS_Store
Expand All @@ -26,3 +30,5 @@ uploads/
# Test artifacts
test_data/
test_questions*.txt
scratch/
tests/scripts/verification_v2.go
50 changes: 50 additions & 0 deletions CLAUDE.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,50 @@
# CLAUDE.md

你是老板的无所不能的助手。

## 默认业务范围

1. 当用户问到财务、销售、经营相关问题时,默认主体是:`南京优集数据科技有限公司(优集公司)` 及其相关业务。
2. 若用户未明确指定其他公司、项目或主体,不主动切换默认主体。

## 数据与回答原则

1. 所有财务回答尽量基于真实数据(数据库、报表、流水)给出结论。
2. 数据不足时,明确说明缺失项,并给出可执行的补充建议;不要编造数据。
3. 回答优先用老板听得懂的业务语言,先给结论,再给简要原因与建议。
4. 涉及收入、成本、利润、销售额时,默认用“银行卡上看/账上看”这类自然说法解释,不要直接说“钱口径/账口径”。

## 过程展示规则

1. 即使底层 skill/工具提供了中间过程(SQL、计算日志、trace),默认也不要在对老板的主回复中展示。
2. 仅在用户明确要求“展示过程/SQL/计算细节”时,再补充中间过程。
3. 如果接口层能返回完整的中间过程、证据等级、SQL 或规则链路,优先完整保留给宿主或前端,不要在桥接层自行裁剪。

## 结果风格

1. 默认把回答写成“老板汇报风格”,先说结果,再说原因,最后说动作建议。
2. 多用老板听得懂的话:
- 用“银行卡上看”“账上看”“实际到手”“实际花出去”“历史欠款回来了”
- 少用“权责发生制”“现金口径”“预提”“递延”“销项/进项差异”这类术语
3. 如果必须提专业概念,要马上翻译成人话,例如:
- “账上看是亏的,但银行卡上这个月其实是净流入”
- “这笔差额主要是税,不是业务少赚了”
4. 不要只丢一个数字,默认按三段式表达:
- 结论:这个月赚了/亏了多少,收了多少钱,花了多少钱
- 原因:差异主要来自哪几个客户、供应商、税或跨月确认
- 动作:接下来该盯哪笔回款、哪项成本、哪类风险
5. 对老板默认更偏“管理判断”,不要写成会计分录讲解。
6. 如果结果不好看,也要直接说清楚,但语气要稳,不要制造惊慌。
7. 金额展示优先让老板容易扫读:
- 金额较大时可同时给“万元”感知和精确元数
- 同一句里不要堆太多小数
8. 对不确定的内容要直接说“目前库里看不出来”或“这笔还需要补结算单/发票/合同台账确认”,不要猜。

## 推荐模板

1. 先结论:
- “先说结果:2 月账上基本打平,银行卡上实际是净流入,说明钱回来了,但不代表当月都算收入。”
2. 再解释:
- “拆开看,金程这笔更像历史应收回款;飞未这部分差额主要是税;林悦和汇智属于供应商付款和成本,不该算到收入差异里。”
3. 最后给动作:
- “接下来建议先盯回款对应的结算单和开票记录,再把大额供应商成本按项目拆开看,老板会更容易判断真实经营情况。”
163 changes: 95 additions & 68 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -7,24 +7,29 @@

### 1. 绝对可靠的数据血缘
摒弃了解析不可控报表的低效路线,系统将最细粒度的**“序时帐”**作为唯一的、确定的数据源,自底向上构建业务:
- 内置 `Python/xlrd` 回落机制,100% 自动修复老式用友/金蝶产生的 OLE2 腐败与空字符串问题。
- `calculator.go`:内建财务自动演算机。不需要人工投喂总结果表,引擎会自动利用财务准则(例如管理费用划归等)聚沙成塔算出科目余额表与月度利润。
- **全格式兼容**:内建 `Python/xlrd` 回落机制,支持老式用友/金蝶产生的 OLE2 腐败文件,并实现了**全自动多页签 (Multi-sheet) 遍历解析**。
- **智能期间识别**:支持复合期间报表(如 `2026.01-2026.02`)的无损提取与分录重组。
- **财务演算引擎**:`calculator.go` 自动利用财务准则聚沙成塔,无需人工结果表即可复现科目余额表与利润逻辑。

### 2. 生态首创的双口径核算
为了调和业务老板(看现金)与审计财务(看税表)的视角差距,系统开创了双视角输出:
* **业务现金流口径(看钱)**:不看纸面报表,直穿 1001/1002 银行科目,排除全部虚拟预提等粉饰动作,告诉你真金白银花哪里了。
* **财务做账口径(看利润)**:严守权责发生制,精准复现次月摊销与年底税前红字冲账影响账面记录的原因。

### 3. 多维度历史折叠与 NLP 分析
针对老板高纬度“人力成本”、“三月销项税”等长尾口语化模糊查询:
- 采用强大的 NLP 数据泛化提取,兼容如 `今年`、`这个月` 或 `三月` 到具体时间轴切片的智能投射保护。
- 自动提取趋势(History),当你询问某一零散类目时,系统会平铺给出其历史脉络及总计汇总。
## 核心能力

- **三位一体身份核验 (Trinity Identity Detector)**:系统不再盲目识别动词,而是通过**银行现金流向(In/Out)**、**会计科目归属(AR/AP)**及**税务特征(进项/销项)**三位一体交叉核验,自动锁定实体身为“客户”、“供应商”或“项目”。
- **数据库辅助识别 (DB-Assisted Recognition)**:集成动态回溯算法,解决口语化提问(如“飞未云科多少钱”)中由于缺少后缀、动词导致的解析难题。
- **审计穿透挖掘 (Summary Penetration)**:自动扫描序时账摘要字段,提取银行流水中缺失的往来单位信息。
- **自动日期锚定 (Dynamic Anchoring)**:智能识别数据库最新业务月份,确保模糊时间查询(如“今年”、“本月”)准确命中。
- **资产负债审计**:实时计算任意日期的科目余额与资产负债表勾稽关系。
- **零配置执行**:支持**项目根目录自动探测**(基于 `go.mod` 自动寻址),确保系统始终准确命中真相源。

## 二、运行与测试指南

### 1. 环境依赖
* **开发环境**:`Go >= 1.20`
* **底层库依赖**:请确保系统已安装 `Python3` 及 `xlrd` 库(用于保障老系统账本解析稳定)
* **底层库依赖(可选)**:`Python3 + xlrd` 仅在解析极老旧 XLS 文件时作为回退路径;常规场景可不安装
* **数据库**:使用原生的 `SQLite3` (默认路径 `finance.db` 和测试表 `test_data/`)。

### 2. 构建与运行
Expand All @@ -43,13 +48,79 @@ go build ./cmd/financeqa/...
### 3. 运行测试套件
新重构版本的测试已深度囊括各项业务边界:
```bash
# 执行测试报告,并一键核验系统的 15 道核心刁钻题
go run scripts/test_runner.go
# 执行审计回归报告,一键核验 15 道核心生产审计刁测题 (南京优集实测集)
/opt/homebrew/bin/go run tests/scripts/prod_audit_regression.go

# 执行后端核心模块单测
go test ./internal/accounting/ -v
```

### 4. 规则配置化(stopwords + 角色阈值)

系统已支持把关键规则从硬编码抽离出来,便于线上快速调参。

1. 默认规则文件:`config/rules.json`
2. 启用文件覆盖:设置 `FINANCEQA_RULES_PATH`
3. 也可用环境变量直接覆盖

```bash
# 方式 1:加载规则文件
FINANCEQA_RULES_PATH=./config/rules.json ./financeqa query --company "南京优集数据科技有限公司" "2026年2月收入/成本/利润分别是多少"

# 方式 2:直接覆盖 stopwords
FINANCEQA_METRIC_STOPWORDS="收入,成本,利润,经营状况" ./financeqa query --company "南京优集数据科技有限公司" "飞未2月收入多少"
```

支持的规则字段(`rules.json`):

1. `generic_metric_stopwords`:泛指标词,避免被误识别成实体。
2. `intent_arap_keywords`:应收/应付/往来类问法关键词。
3. `intent_hr_cost_keywords`:人力成本类高频词,同步用于意图识别与 fallback 路由。
4. `intent_tax_keywords`:税类高频词,例如“税/销项/进项/增值税”。
5. `intent_health_keywords`:经营健康度/状态类问法关键词。
6. `intent_fallback_keywords`:兜底问法关键词。
7. `intent_analysis_keywords`:分析/评分/风险类问法关键词。
8. `intent_host_payload_keywords`:要求输出原始数据包给宿主 LLM 的关键词。
9. `intent_monthly_summary_keywords`:月度经营概括/总结类关键词。
10. `fallback_monthly_expense_keywords`:整体支出/支出汇总类关键词。
11. `role_mixed_min_ratio`:次高分/最高分达到该比例时,判定为 `mixed`。
12. `role_mixed_min_positive_score`:计入“有效角色”的最低分。
13. `role_mixed_min_positive_roles`:触发 `mixed` 所需最少有效角色数量。
14. `role_min_primary_score`:最高分低于该值时,判定为 `unknown`。
15. `role_min_confidence`:置信度低于该值时,判定为 `unknown`。

支持的环境变量覆盖项:

1. `FINANCEQA_RULES_PATH`
2. `FINANCEQA_METRIC_STOPWORDS`(逗号分隔)
3. `FINANCEQA_ROLE_MIXED_MIN_RATIO`
4. `FINANCEQA_ROLE_MIXED_MIN_POSITIVE_SCORE`
5. `FINANCEQA_ROLE_MIXED_MIN_POSITIVE_ROLES`
6. `FINANCEQA_ROLE_MIN_PRIMARY_SCORE`
7. `FINANCEQA_ROLE_MIN_CONFIDENCE`
8. `FINANCEQA_INTENT_ARAP_KEYWORDS`
9. `FINANCEQA_INTENT_HR_COST_KEYWORDS`
10. `FINANCEQA_INTENT_TAX_KEYWORDS`
11. `FINANCEQA_INTENT_HEALTH_KEYWORDS`
12. `FINANCEQA_INTENT_FALLBACK_KEYWORDS`
13. `FINANCEQA_INTENT_ANALYSIS_KEYWORDS`
14. `FINANCEQA_INTENT_HOST_PAYLOAD_KEYWORDS`
15. `FINANCEQA_INTENT_MONTHLY_SUMMARY_KEYWORDS`
16. `FINANCEQA_FALLBACK_MONTHLY_EXPENSE_KEYWORDS`

低频硬编码保留清单:

1. 大额交易识别词:如“最大”“单笔”“流入对手方”“流出对手方”。这类问法比较稳定,且误配风险高,暂时保留在代码里做强约束。
2. 身份识别词:如“是谁”“身份”“谁是”“哪里的”。这类词数量少、语义边界清楚,继续硬编码能减少配置污染。
3. 精确余额词:如“期末”“余额”“查询余额”“还有多少”。这类属于通用财务问法基座,不计划频繁调参。
4. 少量项目组合判断:例如“项目”与“收入/成本/支出/应收/应付/数据出来”的组合分流。这里不仅是关键词命中,还带上下文组合关系,放在代码里更容易保持可读性。

保留原则:

1. 高频、经常需要线上微调的词放到 `rules.json`。
2. 低频、语义稳定、误配代价高的词保留在代码里。
3. 若某类硬编码词在真实老板问法里开始频繁出现变体,再升级为配置项。

## 三、代码集成与调用指南 (API / SDK)

除了使用 CLI 之外,本模块被设计为极具解耦性的 Go SDK。你可以非常简单地将其接入到任何现有的 HTTP 服务(如 Gin/Fiber/HTTPMUX)或者更大的 LLM RAG Agent 层中:
Expand Down Expand Up @@ -93,62 +164,18 @@ func main() {

本项目采用分层解耦的 Go 后端架构,确保了从原始凭证解析到自然语言查询的全链路稳定性。

### 1. 架构图 (Architectural Overview)

```mermaid
graph TB
subgraph "外部数据源 (External Data)"
A1["用友/金蝶 凭证 (.xls)"]
A2["标准银行流水 (.xlsx)"]
end

subgraph "数据接入流水线 (Ingestion Pipeline)"
P["解析层: Parser Layer"]
S["同步逻辑: Sync Logic"]
M["元数据提取与脱敏: Sanitize"]
A1 & A2 --> P
P --> M --> S
end

subgraph "知识库与配置 (Knowledge & Config)"
K["关键词管理: Keywords"]
D["数据库 Schema 与初始化"]
T["全局类型定义: Types"]
end

subgraph "自然语言查询引擎 (Query Engine)"
U["自然语言接口"]
Q["内核引擎: Engine"]
L["中控回退: LLM Fallback (OpenAI)"]
U --> Q
Q <--> L
end

subgraph "核心业务逻辑 (Business Logic)"
C["财务核算: Accounting"]
AN["财务分析: Analysis"]
DIM["会计分期建模: Dimensions"]
end

S --> DB[(SQLite 核心数据库)]
DB <--> DIM
Q --> C & AN
C & AN <--> DB
K -.-> Q

subgraph "应用输出与报表 (Outputs)"
R1["账面利润口径 (Accrual)"]
R2["业务现金流视角 (Cash)"]
R3["风险分析预警 (Alerts)"]
end

C --> R1 & R2
AN --> R3

style DB fill:#f9f,stroke:#333,stroke-width:2px
style L fill:#bbf,stroke:#333,stroke-dasharray: 5 5
style U fill:#dfd,stroke:#333
```
### 1. 架构图(分三张图)

为了提升可读性,原先“一张大图”已拆为三张独立图:

1. [分层架构图(Layered Architecture)](docs/architecture/01-layered-architecture.md)
2. [查询请求时序图(Query Sequence)](docs/architecture/02-query-sequence.md)
3. [部署与运行图(Deployment & Runtime)](docs/architecture/03-deployment-runtime.md)

阅读建议:
1. 先看分层图,理解系统边界;
2. 再看时序图,理解一次查询如何流转;
3. 最后看部署图,理解线上/本地如何运行与接入。

### 2. 逻辑分层
* **接入层 (Parser & Ingest)**:处理各版本用友、金蝶及银行导出的 Excel 原始数据。具备自动脱敏、元数据提取(日期/公司识别)及数据清洗能力。
Expand Down Expand Up @@ -185,7 +212,7 @@ finance_qa/

### 1. 环境依赖
* **Go**: `>= 1.20`
* **Python3**: 部分老旧 XLS 解析需依赖 `xlrd` 插件作为容错回退
* **Python3(可选)**: 仅在极老旧 XLS 容错回退场景下需要 `xlrd`。
* **环境变量**: 若需启用 LLM 回退功能,请配置 `OPENAI_API_KEY`。

### 2. 运行测试
Expand All @@ -197,6 +224,6 @@ go test ./internal/...
# 运行集成测试 (全量覆盖业务场景)
go test ./tests/integration/...

# 运行回归检查工具 (自动输出 15 道题的回答对比)
go run tests/scripts/test_runner.go
# 运行回归检查工具 (自动输出 15 道生产提问的审计对照表)
/opt/homebrew/bin/go run tests/scripts/prod_audit_regression.go
```
Loading
Loading