WIP
This commit is contained in:
48
README.md
48
README.md
@@ -1,14 +1,14 @@
|
||||
# Invoice Master POC v2
|
||||
|
||||
自动发票字段提取系统 - 使用 YOLOv11 + PaddleOCR 从瑞典 PDF 发票中提取结构化数据。
|
||||
自动发票字段提取系统 - 使用 YOLO26 + PaddleOCR 从瑞典 PDF 发票中提取结构化数据。
|
||||
|
||||
## 项目概述
|
||||
|
||||
本项目实现了一个完整的发票字段自动提取流程:
|
||||
|
||||
1. **自动标注**: 利用已有 CSV 结构化数据 + OCR 自动生成 YOLO 训练标注
|
||||
2. **模型训练**: 使用 YOLOv11 训练字段检测模型,支持数据增强
|
||||
3. **推理提取**: 检测字段区域 -> OCR 提取文本 -> 字段规范化
|
||||
1. **自动标注**: 利用已有 CSV 结构化数据 + OCR 自动生成 YOLO 训练标注(统一 15px 填充)
|
||||
2. **模型训练**: 使用 YOLO26 训练字段检测模型,支持数据增强
|
||||
3. **推理提取**: 检测字段区域 -> OCR 提取文本 -> ValueSelector 过滤标签 -> 字段规范化
|
||||
4. **Web 管理**: React 前端 + FastAPI 后端,支持文档管理、数据集构建、模型训练和版本管理
|
||||
|
||||
### 架构
|
||||
@@ -37,8 +37,8 @@ frontend/ # React 前端 (Vite + TypeScript + TailwindCSS)
|
||||
|------|------|
|
||||
| **已标注文档** | 9,738 (9,709 成功) |
|
||||
| **总体字段匹配率** | 94.8% (82,604/87,121) |
|
||||
| **测试** | 2,058 passed |
|
||||
| **测试覆盖率** | 60% |
|
||||
| **测试** | 2,047 passed |
|
||||
| **测试覆盖率** | 72% |
|
||||
| **模型 mAP@0.5** | 93.5% |
|
||||
|
||||
**各字段匹配率:**
|
||||
@@ -204,7 +204,7 @@ invoice-master-poc-v2/
|
||||
│ ├── run_server.py # Web 服务器入口
|
||||
│ └── backend/
|
||||
│ ├── cli/ # infer, serve
|
||||
│ ├── pipeline/ # YOLO 检测, 字段提取, 解析器
|
||||
│ ├── pipeline/ # YOLO 检测, 字段提取, ValueSelector, 解析器
|
||||
│ ├── web/ # FastAPI 应用
|
||||
│ │ ├── api/v1/ # REST API (admin, public, batch)
|
||||
│ │ ├── schemas/ # Pydantic 数据模型
|
||||
@@ -278,7 +278,7 @@ python -m training.cli.autolabel --workers 4
|
||||
```bash
|
||||
# 从预训练模型开始训练
|
||||
python -m training.cli.train \
|
||||
--model yolo11n.pt \
|
||||
--model yolo26s.pt \
|
||||
--epochs 100 \
|
||||
--batch 16 \
|
||||
--name invoice_fields \
|
||||
@@ -286,7 +286,7 @@ python -m training.cli.train \
|
||||
|
||||
# 低内存模式
|
||||
python -m training.cli.train \
|
||||
--model yolo11n.pt \
|
||||
--model yolo26s.pt \
|
||||
--epochs 100 \
|
||||
--name invoice_fields \
|
||||
--low-memory
|
||||
@@ -443,6 +443,30 @@ result = parser.parse("Said, Shakar Umj 436-R Billo")
|
||||
print(f"Customer Number: {result}") # "UMJ 436-R"
|
||||
```
|
||||
|
||||
## 推理流水线 (Two-Stage Detection)
|
||||
|
||||
```
|
||||
YOLO bbox -> crop -> PaddleOCR -> [all tokens] -> ValueSelector -> normalizer
|
||||
| |
|
||||
individual selected
|
||||
text lines value token(s)
|
||||
```
|
||||
|
||||
**BBox 扩展**: 所有字段统一使用 15px 填充(150 DPI 下约 2.5mm),不做方向性扩展,不依赖布局假设。
|
||||
|
||||
**ValueSelector**: 在 OCR 和 normalizer 之间按字段类型过滤标签文本,只保留值 token:
|
||||
|
||||
| 字段 | 选择策略 | 示例输入 -> 输出 |
|
||||
|------|---------|-----------------|
|
||||
| InvoiceDate / DueDate | 日期模式匹配 | "Fakturadatum 2024-01-15" -> "2024-01-15" |
|
||||
| Amount | 金额模式匹配 | "Belopp 1 234,56 kr" -> "1 234,56" |
|
||||
| Bankgiro / Plusgiro | Giro 号码模式 | "BG: 123-4567" -> "123-4567" |
|
||||
| OCR | 最长数字序列 (>=5位) | "OCR 94228110015950070" -> "94228110015950070" |
|
||||
| InvoiceNumber | 排除瑞典语标签 | "Fakturanr INV-2024-001" -> "INV-2024-001" |
|
||||
| payment_line | 保留全部 | 不过滤 |
|
||||
|
||||
如果没有匹配到任何模式,回退返回全部 token(永远不会比之前更差)。
|
||||
|
||||
## DPI 配置
|
||||
|
||||
系统所有组件统一使用 **150 DPI**。DPI 必须在训练和推理时保持一致。
|
||||
@@ -506,9 +530,9 @@ DB_PASSWORD=xxx pytest tests/ --cov=packages --cov-report=term-missing
|
||||
|
||||
| 指标 | 数值 |
|
||||
|------|------|
|
||||
| **测试总数** | 2,058 |
|
||||
| **测试总数** | 2,047 |
|
||||
| **通过率** | 100% |
|
||||
| **覆盖率** | 60% |
|
||||
| **覆盖率** | 72% |
|
||||
|
||||
## 存储抽象层
|
||||
|
||||
@@ -619,7 +643,7 @@ npm run dev
|
||||
|
||||
| 组件 | 技术 |
|
||||
|------|------|
|
||||
| **目标检测** | YOLOv11 (Ultralytics) |
|
||||
| **目标检测** | YOLO26 (Ultralytics >= 8.4.0) |
|
||||
| **OCR 引擎** | PaddleOCR v5 (PP-OCRv5) |
|
||||
| **PDF 处理** | PyMuPDF (fitz) |
|
||||
| **数据库** | PostgreSQL + SQLModel |
|
||||
|
||||
Reference in New Issue
Block a user