Invoice Master POC v2

自动发票字段提取系统 - 使用 YOLOv11 + PaddleOCR 从瑞典 PDF 发票中提取结构化数据。

项目概述

本项目实现了一个完整的发票字段自动提取流程:

  1. 自动标注: 利用已有 CSV 结构化数据 + OCR 自动生成 YOLO 训练标注
  2. 模型训练: 使用 YOLOv11 训练字段检测模型
  3. 推理提取: 检测字段区域 → OCR 提取文本 → 字段规范化

当前进度

指标 数值
已标注文档 9,738 (9,709 成功)
总体字段匹配率 94.8% (82,604/87,121)

各字段匹配率:

字段 匹配率 说明
supplier_accounts(Bankgiro) 100.0% 供应商 Bankgiro
supplier_accounts(Plusgiro) 100.0% 供应商 Plusgiro
Plusgiro 99.4% 支付 Plusgiro
OCR 99.1% OCR 参考号
Bankgiro 99.0% 支付 Bankgiro
InvoiceNumber 98.9% 发票号码
InvoiceDueDate 95.9% 到期日期
InvoiceDate 95.5% 发票日期
Amount 91.3% 金额
supplier_organisation_number 78.2% 供应商组织号 (CSV 数据质量问题)

运行环境

本项目必须WSL + Conda 环境中运行。

系统要求

环境 要求
WSL WSL 2 + Ubuntu 22.04
Conda Miniconda 或 Anaconda
Python 3.10+ (通过 Conda 管理)
GPU NVIDIA GPU + CUDA 12.x (强烈推荐)
数据库 PostgreSQL (存储标注结果)

功能特点

  • 双模式 PDF 处理: 支持文本层 PDF 和扫描图 PDF
  • 自动标注: 利用已有 CSV 结构化数据自动生成 YOLO 训练数据
  • 多策略字段匹配: 精确匹配、子串匹配、规范化匹配
  • 数据库存储: 标注结果存储在 PostgreSQL支持增量处理和断点续传
  • YOLO 检测: 使用 YOLOv11 检测发票字段区域
  • OCR 识别: 使用 PaddleOCR v5 提取检测区域的文本
  • Web 应用: 提供 REST API 和可视化界面
  • 增量训练: 支持在已训练模型基础上继续训练

支持的字段

类别 ID 字段名 说明
0 invoice_number 发票号码
1 invoice_date 发票日期
2 invoice_due_date 到期日期
3 ocr_number OCR 参考号 (瑞典支付系统)
4 bankgiro Bankgiro 号码
5 plusgiro Plusgiro 号码
6 amount 金额
7 supplier_organisation_number 供应商组织号

安装

# 1. 进入 WSL
wsl -d Ubuntu-22.04

# 2. 创建 Conda 环境
conda create -n invoice-py311 python=3.11 -y
conda activate invoice-py311

# 3. 进入项目目录
cd /mnt/c/Users/yaoji/git/ColaCoder/invoice-master-poc-v2

# 4. 安装依赖
pip install -r requirements.txt

# 5. 安装 Web 依赖
pip install uvicorn fastapi python-multipart pydantic

快速开始

1. 准备数据

~/invoice-data/
├── raw_pdfs/
│   ├── {DocumentId}.pdf
│   └── ...
├── structured_data/
│   └── document_export_YYYYMMDD.csv
└── dataset/
    └── temp/  (渲染的图片)

CSV 格式:

DocumentId,InvoiceDate,InvoiceNumber,InvoiceDueDate,OCR,Bankgiro,Plusgiro,Amount
3be53fd7-...,2025-12-13,100017500321,2026-01-03,100017500321,53939484,,114

2. 自动标注

# 使用双池模式 (CPU + GPU)
python -m src.cli.autolabel \
    --dual-pool \
    --cpu-workers 3 \
    --gpu-workers 1

# 单线程模式
python -m src.cli.autolabel --workers 4

3. 训练模型

# 从预训练模型开始训练
python -m src.cli.train \
    --model yolo11n.pt \
    --epochs 100 \
    --batch 16 \
    --name invoice_yolo11n_full \
    --dpi 150

4. 增量训练

当添加新数据后,可以在已训练模型基础上继续训练:

# 从已训练的 best.pt 继续训练
python -m src.cli.train \
    --model runs/train/invoice_yolo11n_full/weights/best.pt \
    --epochs 30 \
    --batch 16 \
    --name invoice_yolo11n_v2 \
    --dpi 150

增量训练建议:

场景 建议
添加少量新数据 (<20%) 继续训练 10-30 epochs
添加大量新数据 (>50%) 继续训练 50-100 epochs
修正大量标注错误 从头训练
添加新的字段类型 从头训练

5. 推理

# 命令行推理
python -m src.cli.infer \
    --model runs/train/invoice_yolo11n_full/weights/best.pt \
    --input path/to/invoice.pdf \
    --output result.json \
    --gpu

6. Web 应用

# 启动 Web 服务器
python run_server.py --port 8000

# 开发模式 (自动重载)
python run_server.py --debug --reload

# 禁用 GPU
python run_server.py --no-gpu

访问 http://localhost:8000 使用 Web 界面。

Web API 端点

方法 端点 描述
GET / Web UI 界面
GET /api/v1/health 健康检查
POST /api/v1/infer 上传文件并推理
GET /api/v1/results/{filename} 获取可视化图片

训练配置

YOLO 训练参数

python -m src.cli.train [OPTIONS]

Options:
  --model, -m        基础模型 (默认: yolo11n.pt)
  --epochs, -e       训练轮数 (默认: 100)
  --batch, -b        批大小 (默认: 16)
  --imgsz            图像尺寸 (默认: 1280)
  --dpi              PDF 渲染 DPI (默认: 150)
  --name             训练名称
  --limit            限制文档数 (用于测试)
  --device           设备 (0=GPU, cpu)

训练最佳实践

  1. 禁用翻转增强 (文本检测):

    fliplr=0.0, flipud=0.0
    
  2. 使用 Early Stopping:

    patience=20
    
  3. 启用 AMP (混合精度训练):

    amp=True
    
  4. 保存检查点:

    save_period=10
    

训练结果示例

使用约 10,000 张训练图片100 epochs 后的结果:

指标
mAP@0.5 98.7%
mAP@0.5-0.95 87.4%
Precision 97.5%
Recall 95.5%

注:目前仍在持续标注更多数据,预计最终将有 25,000+ 张标注图片用于训练。

项目结构

invoice-master-poc-v2/
├── src/
│   ├── cli/              # 命令行工具
│   │   ├── autolabel.py  # 自动标注
│   │   ├── train.py      # 模型训练
│   │   ├── infer.py      # 推理
│   │   └── serve.py      # Web 服务器
│   ├── pdf/              # PDF 处理
│   │   ├── extractor.py  # 文本提取
│   │   ├── renderer.py   # 图像渲染
│   │   └── detector.py   # 类型检测
│   ├── ocr/              # PaddleOCR 封装
│   ├── normalize/        # 字段规范化
│   ├── matcher/          # 字段匹配
│   ├── yolo/             # YOLO 相关
│   │   ├── annotation_generator.py
│   │   └── db_dataset.py
│   ├── inference/        # 推理管道
│   │   ├── pipeline.py
│   │   ├── yolo_detector.py
│   │   └── field_extractor.py
│   ├── processing/       # 多池处理架构
│   │   ├── worker_pool.py
│   │   ├── cpu_pool.py
│   │   ├── gpu_pool.py
│   │   ├── task_dispatcher.py
│   │   └── dual_pool_coordinator.py
│   ├── web/              # Web 应用
│   │   ├── app.py        # FastAPI 应用
│   │   ├── routes.py     # API 路由
│   │   ├── services.py   # 业务逻辑
│   │   ├── schemas.py    # 数据模型
│   │   └── config.py     # 配置
│   └── data/             # 数据处理
├── config.py             # 配置文件
├── run_server.py         # Web 服务器启动脚本
├── runs/                 # 训练输出
│   └── train/
│       └── invoice_yolo11n_full/
│           └── weights/
│               ├── best.pt
│               └── last.pt
└── requirements.txt

多池处理架构

项目使用 CPU + GPU 双池架构处理不同类型的 PDF

┌─────────────────────────────────────────────────────┐
│              DualPoolCoordinator                     │
│  ┌─────────────────┐    ┌─────────────────┐        │
│  │   CPU Pool      │    │   GPU Pool      │        │
│  │  (3 workers)    │    │  (1 worker)     │        │
│  │                 │    │                 │        │
│  │  Text PDFs      │    │  Scanned PDFs   │        │
│  │  ~50-87 it/s    │    │  ~1-2 it/s      │        │
│  └─────────────────┘    └─────────────────┘        │
│                                                     │
│  TaskDispatcher: 根据 PDF 类型分配任务               │
└─────────────────────────────────────────────────────┘

关键设计

  • spawn 启动方式: 兼容 CUDA 多进程
  • as_completed(): 无死锁结果收集
  • 进程初始化器: 每个 worker 加载一次模型
  • 协调器持久化: 跨 CSV 文件复用 worker 池

配置文件

config.py

# 数据库配置
DATABASE = {
    'host': '192.168.68.31',
    'port': 5432,
    'database': 'docmaster',
    'user': 'docmaster',
    'password': '******',
}

# 路径配置
PATHS = {
    'csv_dir': '~/invoice-data/structured_data',
    'pdf_dir': '~/invoice-data/raw_pdfs',
    'output_dir': '~/invoice-data/dataset',
}

CLI 命令参考

autolabel

python -m src.cli.autolabel [OPTIONS]

Options:
  --csv, -c          CSV 文件路径 (支持 glob)
  --pdf-dir, -p      PDF 文件目录
  --output, -o       输出目录
  --workers, -w      单线程模式 worker 数 (默认: 4)
  --dual-pool        启用双池模式
  --cpu-workers      CPU 池 worker 数 (默认: 3)
  --gpu-workers      GPU 池 worker 数 (默认: 1)
  --dpi              渲染 DPI (默认: 150)
  --limit, -l        限制处理文档数

train

python -m src.cli.train [OPTIONS]

Options:
  --model, -m        基础模型路径
  --epochs, -e       训练轮数 (默认: 100)
  --batch, -b        批大小 (默认: 16)
  --imgsz            图像尺寸 (默认: 1280)
  --dpi              PDF 渲染 DPI (默认: 150)
  --name             训练名称
  --limit            限制文档数

infer

python -m src.cli.infer [OPTIONS]

Options:
  --model, -m        模型路径
  --input, -i        输入 PDF/图像
  --output, -o       输出 JSON 路径
  --confidence       置信度阈值 (默认: 0.5)
  --dpi              渲染 DPI (默认: 300)
  --gpu              使用 GPU

serve

python run_server.py [OPTIONS]

Options:
  --host             绑定地址 (默认: 0.0.0.0)
  --port             端口 (默认: 8000)
  --model, -m        模型路径
  --confidence       置信度阈值 (默认: 0.3)
  --dpi              渲染 DPI (默认: 150)
  --no-gpu           禁用 GPU
  --reload           开发模式自动重载
  --debug            调试模式

Python API

from src.inference import InferencePipeline

# 初始化
pipeline = InferencePipeline(
    model_path='runs/train/invoice_yolo11n_full/weights/best.pt',
    confidence_threshold=0.3,
    use_gpu=True,
    dpi=150
)

# 处理 PDF
result = pipeline.process_pdf('invoice.pdf')

# 处理图片
result = pipeline.process_image('invoice.png')

# 获取结果
print(result.fields)       # {'InvoiceNumber': '12345', 'Amount': '1234.56', ...}
print(result.confidence)   # {'InvoiceNumber': 0.95, 'Amount': 0.92, ...}
print(result.to_json())    # JSON 格式输出

开发状态

  • 文本层 PDF 自动标注
  • 扫描图 OCR 自动标注
  • 多策略字段匹配 (精确/子串/规范化)
  • PostgreSQL 数据库存储 (断点续传)
  • 信号处理和超时保护
  • YOLO 训练 (98.7% mAP@0.5)
  • 推理管道
  • 字段规范化和验证
  • Web 应用 (FastAPI + 前端 UI)
  • 增量训练支持
  • 完成全部 25,000+ 文档标注
  • 表格 items 处理
  • 模型量化部署

技术栈

组件 技术
目标检测 YOLOv11 (Ultralytics)
OCR 引擎 PaddleOCR v5 (PP-OCRv5)
PDF 处理 PyMuPDF (fitz)
数据库 PostgreSQL + psycopg2
Web 框架 FastAPI + Uvicorn
深度学习 PyTorch + CUDA

许可证

MIT License

Description
No description provided
Readme 2.1 MiB
Languages
Python 91.5%
TypeScript 7.7%
Shell 0.7%