数据提取规则系统设计.md 30 KB

数据提取规则系统设计文档

版本: 2.0.0 日期: 2026-01-23 作者: AI Assistant (Claude Opus 4.5)

一、概述

1.1 背景

在电力工程预评价报告生成场景中,用户需要从多个来源文档(PDF、Word、Excel)中提取特定数据,生成标准化的报告。

核心痛点

  • 不同工程项目的报告结构相似,但数据不同
  • 人工从多个文档中复制粘贴数据,效率低、易出错
  • 相同类型的报告需要重复劳动

解决方案: 用户上传一份已完成的真实报告作为示例,在报告中标记变量(如工程名称、批复日期等),并配置每个变量的数据来源。之后遇到同类项目,只需替换来源文件,系统自动提取数据生成新报告。

1.2 核心概念

概念 说明
模板(Template) 基于真实报告创建,包含变量定义和来源文件配置
来源文件定义(SourceFile) 模板需要的来源文件类型,用别名标识(如"可研批复")
变量(Variable) 报告中需要动态替换的内容,绑定到文档中的具体位置
生成任务(Generation) 使用模板生成新报告的一次任务

1.3 设计原则

  1. 示例驱动:基于真实报告创建模板,所见即所得
  2. 数据溯源:每个提取值都能追溯到来源文档的具体位置
  3. 灵活来源:来源文件数量和类型由用户自定义
  4. 一次配置,多次复用:模板创建后可用于生成任意多份新报告

二、用户使用流程

2.1 流程概览

┌─────────────────────────────────────────────────────────────────┐
│                     第一次:创建模板                             │
├─────────────────────────────────────────────────────────────────┤
│                                                                  │
│  1. 上传示例报告(一份真实的、完整的报告)                        │
│     "襄阳连云110kV预评价报告.docx"                               │
│                                                                  │
│  2. 添加来源文件(自定义数量和别名)                              │
│     ├── 可研批复.pdf      别名:"可研批复"                       │
│     ├── 站址报告.docx     别名:"站址报告"                       │
│     └── 概算表.xlsx       别名:"概算表"                         │
│                                                                  │
│  3. 在示例报告中标记变量                                         │
│     选中文本 "襄阳连云 110kV 输变电工程"                         │
│         → 设为变量 "project_name"                                │
│         → 来源:从【可研批复】第1页 AI提取                       │
│                                                                  │
│  4. 保存模板                                                     │
│                                                                  │
└─────────────────────────────────────────────────────────────────┘
                              ↓
┌─────────────────────────────────────────────────────────────────┐
│                    第二次起:使用模板生成新报告                   │
├─────────────────────────────────────────────────────────────────┤
│                                                                  │
│  1. 选择模板                                                     │
│                                                                  │
│  2. 上传新项目的来源文件(按别名对应)                            │
│     ├── 武汉东湖批复.pdf    → "可研批复"                         │
│     ├── 武汉站址报告.docx   → "站址报告"                         │
│     └── 武汉概算.xlsx       → "概算表"                           │
│                                                                  │
│  3. 点击【生成】                                                 │
│     系统自动:                                                   │
│     - 从新文件提取数据                                           │
│     - 替换模板中的变量                                           │
│     - 生成新报告                                                 │
│                                                                  │
│  4. 预览、确认、下载                                             │
│     "武汉东湖110kV预评价报告.docx"                               │
│                                                                  │
└─────────────────────────────────────────────────────────────────┘

2.2 变量标记交互

用户在文档编辑器中操作:

┌─────────────────────────────────────────────────────────────────┐
│  📄 示例报告编辑器                                               │
├─────────────────────────────────────────────────────────────────┤
│                                                                  │
│  一、项目概述                                                    │
│                                                                  │
│  1.1 工程名称:襄阳连云 110kV 输变电工程                         │
│                ═══════════════════════════ ← 用户选中这段文字    │
│                         │                                        │
│                         ▼ 右键菜单                               │
│      ┌────────────────────────────────────┐                     │
│      │ 📌 设为变量                         │                     │
│      │                                    │                     │
│      │ 变量名:project_name               │                     │
│      │ 显示名:工程名称                   │                     │
│      │                                    │                     │
│      │ 当前值:襄阳连云 110kV 输变电工程   │                     │
│      │                                    │                     │
│      │ 数据来源:                         │                     │
│      │ ● 从来源文件提取                   │                     │
│      │   ├─ 来源文件:[可研批复 ▼]        │                     │
│      │   ├─ 定位方式:[按页码 ▼]          │                     │
│      │   ├─ 页码范围:1-2                 │                     │
│      │   └─ 提取方式:[AI提取 ▼]          │                     │
│      │      └─ 提取目标:工程项目名称     │                     │
│      │                                    │                     │
│      │ ○ 手动输入                         │                     │
│      │ ○ 引用其他变量                     │                     │
│      │ ○ 固定值(不变)                   │                     │
│      │                                    │                     │
│      │           [取消]  [确定]           │                     │
│      └────────────────────────────────────┘                     │
│                                                                  │
│  1.2 建设单位:【$construction_unit】← 已标记的变量高亮显示      │
│                                                                  │
│  1.3 批复日期:【$approval_date】                                │
│                                                                  │
└─────────────────────────────────────────────────────────────────┘

三、系统架构

3.1 整体架构图

┌─────────────────────────────────────────────────────────────────────────────┐
│                              前端 (Vue.js / Flutter)                         │
│  ┌──────────────┐  ┌──────────────┐  ┌──────────────┐  ┌──────────────┐    │
│  │ 模板管理     │  │ 文档编辑器   │  │ 变量配置     │  │ 报告生成     │    │
│  └──────────────┘  └──────────────┘  └──────────────┘  └──────────────┘    │
└─────────────────────────────────────────────────────────────────────────────┘
                                       │
                                       ▼
┌─────────────────────────────────────────────────────────────────────────────┐
│                              API Gateway                                     │
└─────────────────────────────────────────────────────────────────────────────┘
                                       │
          ┌────────────────────────────┼────────────────────────────┐
          ▼                            ▼                            ▼
┌──────────────────────┐  ┌──────────────────────┐  ┌──────────────────────┐
│   template-service   │  │   document-service   │  │     ai-service       │
│   (模板与生成)       │  │   (文档管理)         │  │     (AI提取)         │
│  ┌────────────────┐  │  │  ┌────────────────┐  │  │  ┌────────────────┐  │
│  │ TemplateService│  │  │  │ DocumentService│  │  │  │ DeepSeekClient │  │
│  │ VariableService│  │  │  │ ElementService │  │  │  │ AIExtractService│ │
│  │ GenerationSvc  │  │  │  └────────────────┘  │  │  └────────────────┘  │
│  └────────────────┘  │  └──────────────────────┘  └──────────────────────┘
└──────────────────────┘
          │                            │                            │
          └────────────────────────────┴────────────────────────────┘
                                       │
                                       ▼
┌─────────────────────────────────────────────────────────────────────────────┐
│                           PostgreSQL + Redis                                 │
└─────────────────────────────────────────────────────────────────────────────┘

3.2 模块职责

模块 职责 位置
template-service 模板管理、变量配置、报告生成(重构 extract-service) backend/extract-service
document-service 文档管理、元素存储(已有) backend/document-service
parse-service 文档解析、结构化提取(已有) backend/parse-service
ai-service AI 提取、总结(已有) backend/ai-service

四、数据库设计

4.1 ER 图

┌─────────────────┐       ┌─────────────────┐       ┌─────────────────┐
│    templates    │       │  source_files   │       │   variables     │
├─────────────────┤       ├─────────────────┤       ├─────────────────┤
│ id              │◄──────│ template_id     │       │ id              │
│ user_id         │       │ id              │       │ template_id     │──────►│
│ name            │       │ alias           │◄──────│ source_file_alias│      │
│ description     │       │ description     │       │ name            │      │
│ base_document_id│       │ file_types      │       │ display_name    │      │
│ status          │       │ required        │       │ location        │      │
│ config          │       │ example_doc_id  │       │ example_value   │      │
│ created_at      │       │ display_order   │       │ source_type     │      │
│ updated_at      │       └─────────────────┘       │ source_config   │      │
└─────────────────┘                                 │ extract_type    │      │
        │                                           │ extract_config  │      │
        │       ┌─────────────────┐                 │ display_order   │      │
        │       │   generations   │                 └─────────────────┘      │
        │       ├─────────────────┤                                          │
        └──────►│ template_id     │                                          │
                │ id              │◄─────────────────────────────────────────┘
                │ user_id         │       (通过 template_id 关联)
                │ name            │
                │ source_file_map │  ← JSONB: {"可研批复": "doc_123", ...}
                │ variable_values │  ← JSONB: {"project_name": {...}, ...}
                │ output_doc_id   │
                │ status          │
                          │ created_at      │
                │ completed_at    │
                          └─────────────────┘

4.2 表结构定义

4.2.1 templates(模板表)

CREATE TABLE templates (
    id VARCHAR(36) PRIMARY KEY,
    user_id VARCHAR(36) NOT NULL,
    name VARCHAR(255) NOT NULL COMMENT '模板名称',
    description TEXT COMMENT '模板描述',
    base_document_id VARCHAR(36) NOT NULL COMMENT '示例报告文档ID',
    status VARCHAR(32) DEFAULT 'draft' COMMENT '状态: draft/published/archived',
    config JSONB COMMENT '模板配置',
    is_public BOOLEAN DEFAULT FALSE COMMENT '是否公开',
    use_count INT DEFAULT 0 COMMENT '使用次数',
    create_time TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
    update_time TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
    create_by VARCHAR(36),
    update_by VARCHAR(36)
);

CREATE INDEX idx_templates_user_id ON templates(user_id);
CREATE INDEX idx_templates_status ON templates(status);

COMMENT ON TABLE templates IS '报告模板';

4.2.2 source_files(来源文件定义表)

CREATE TABLE source_files (
    id VARCHAR(36) PRIMARY KEY,
    template_id VARCHAR(36) NOT NULL REFERENCES templates(id) ON DELETE CASCADE,
    alias VARCHAR(100) NOT NULL COMMENT '文件别名,如"可研批复"',
    description TEXT COMMENT '文件说明',
    file_types JSONB COMMENT '允许的文件类型: ["pdf", "docx"]',
    required BOOLEAN DEFAULT TRUE COMMENT '是否必须',
    example_document_id VARCHAR(36) COMMENT '创建模板时使用的示例文件',
    display_order INT DEFAULT 0 COMMENT '显示顺序',
    create_time TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
    
    UNIQUE (template_id, alias)
);

CREATE INDEX idx_source_files_template ON source_files(template_id);

COMMENT ON TABLE source_files IS '来源文件定义';

4.2.3 variables(变量表)

CREATE TABLE variables (
    id VARCHAR(36) PRIMARY KEY,
    template_id VARCHAR(36) NOT NULL REFERENCES templates(id) ON DELETE CASCADE,
    
    -- 变量标识
    name VARCHAR(100) NOT NULL COMMENT '变量名(程序用)',
    display_name VARCHAR(200) NOT NULL COMMENT '显示名称',
    variable_group VARCHAR(100) COMMENT '变量分组',
    
    -- 在示例报告中的位置
    location JSONB NOT NULL COMMENT '文档中的位置',
    -- location 结构:
    -- {
    --   "element_id": "elem_001",
    --   "type": "text" | "table_cell" | "paragraph",
    --   "start_offset": 10,
    --   "end_offset": 35,
    --   "row_index": 2,        -- 表格行
    --   "col_index": 1         -- 表格列
    -- }
    
    -- 示例值(原文档中的值)
    example_value TEXT COMMENT '示例值',
    value_type VARCHAR(32) DEFAULT 'text' COMMENT '值类型: text/date/number/table',
    
    -- 数据来源
    source_file_alias VARCHAR(100) COMMENT '来源文件别名',
    source_type VARCHAR(32) NOT NULL COMMENT '来源类型: document/manual/reference/fixed',
    source_config JSONB COMMENT '来源配置',
    -- source_config 示例(document类型):
    -- {
    --   "location": {
    --     "type": "page",
    --     "pageStart": 1,
    --     "pageEnd": 2
    --   }
    -- }
    
    -- 提取方式
    extract_type VARCHAR(32) COMMENT '提取类型: direct/ai_extract/ai_summarize',
    extract_config JSONB COMMENT '提取配置',
    -- extract_config 示例(ai_extract类型):
    -- {
    --   "targetDescription": "提取工程名称",
    --   "fieldType": "text",
    --   "expectedFormat": "XX市XX工程"
    -- }
    
    display_order INT DEFAULT 0 COMMENT '显示顺序',
    create_time TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
    update_time TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
    
    UNIQUE (template_id, name)
);

CREATE INDEX idx_variables_template ON variables(template_id);

COMMENT ON TABLE variables IS '模板变量';

4.2.4 generations(生成任务表)

CREATE TABLE generations (
    id VARCHAR(36) PRIMARY KEY,
    template_id VARCHAR(36) NOT NULL REFERENCES templates(id),
    user_id VARCHAR(36) NOT NULL,
    
    name VARCHAR(255) COMMENT '任务名称',
    
    -- 来源文件映射:别名 → 文档ID
    source_file_map JSONB NOT NULL COMMENT '来源文件映射',
    -- 示例:{"可研批复": "doc_123", "站址报告": "doc_456"}
    
    -- 变量提取结果
    variable_values JSONB COMMENT '变量值',
    -- 示例:
    -- {
    --   "project_name": {
    --     "value": "武汉东湖 110kV 输变电工程",
    --     "confidence": 0.96,
    --     "source_preview": "...",
    --     "status": "extracted"
    --   }
    -- }
    
    -- 生成的文档
    output_document_id VARCHAR(36) COMMENT '输出文档ID',
    
    status VARCHAR(32) DEFAULT 'pending' COMMENT '状态: pending/extracting/review/completed/error',
    error_message TEXT COMMENT '错误信息',
    
    create_time TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
    completed_at TIMESTAMP COMMENT '完成时间'
);

CREATE INDEX idx_generations_template ON generations(template_id);
CREATE INDEX idx_generations_user ON generations(user_id);
CREATE INDEX idx_generations_status ON generations(status);

COMMENT ON TABLE generations IS '报告生成任务';

五、变量来源类型

5.1 来源类型总览

来源类型 说明 适用场景
document 从来源文件提取 工程名称、批复日期等需要从文档中获取的信息
manual 手动输入 联系人、特殊备注等无法自动获取的信息
reference 引用其他变量 组合已提取的值,如"《{project_name}可行性研究报告》"
fixed 固定值 不随项目变化的固定文本

5.2 document 类型配置

{
  "source_file_alias": "可研批复",
  "source_type": "document",
  "source_config": {
  "location": {
      "type": "page",           // page | chapter | element
    "pageStart": 1,
    "pageEnd": 2,
      "paragraphKeyword": null  // 可选:段落关键词过滤
    }
  },
  "extract_type": "ai_extract",
  "extract_config": {
    "targetDescription": "从批复文件中提取工程项目的完整名称",
    "fieldType": "text",
    "expectedFormat": "XX市XX工程",
    "examples": ["襄阳连云220千伏输变电工程"]
  }
}

5.3 manual 类型配置

{
  "source_type": "manual",
  "source_config": {
    "placeholder": "请输入项目联系人姓名",
    "required": true,
    "defaultValue": "",
    "inputType": "text",        // text | textarea | date | number
    "validation": {
      "maxLength": 50,
      "pattern": "^[\\u4e00-\\u9fa5]{2,10}$"
    }
  }
}

5.4 reference 类型配置

{
  "source_type": "reference",
  "source_config": {
    "referenceVariables": ["project_name", "design_unit", "report_date"],
    "combineTemplate": "《{project_name}可行性研究报告》由{design_unit}于{report_date}编制",
  "transform": {
      "type": "format",
      "formatPattern": "{0}"
    }
  }
}

5.5 fixed 类型配置

{
  "source_type": "fixed",
  "source_config": {
    "fixedValue": "本报告依据《电力建设工程预算编制办法》(2018版)编制。"
  }
}

六、提取类型

6.1 提取类型总览

提取类型 说明 适用场景
direct 直接提取 定位到的内容直接使用
ai_extract AI字段提取 从一段文本中提取特定字段
ai_summarize AI总结 对内容进行总结提炼

6.2 direct 配置

{
  "extract_type": "direct",
  "extract_config": {
    "trimWhitespace": true,
    "removeLineBreaks": false,
    "mergeSpaces": true
  }
}

6.3 ai_extract 配置

{
  "extract_type": "ai_extract",
  "extract_config": {
    "targetDescription": "从批复文件中提取可研批复的日期",
  "fieldType": "date",
  "expectedFormat": "YYYY年MM月DD日",
  "examples": ["2024年5月15日", "2023年12月1日"]
}
}

6.4 ai_summarize 配置

{
  "extract_type": "ai_summarize",
  "extract_config": {
  "summarizePrompt": "请对以下内容进行总结,重点描述项目建设的必要性",
  "focusPoints": ["建设背景", "现状问题", "建设目的"],
    "rules": ["使用正式的工程报告语言", "保留关键的数据和指标"],
  "style": "formal",
    "maxLength": 300
  }
}

七、API 设计

7.1 模板管理 API

方法 路径 说明
POST /api/v1/templates 创建模板
GET /api/v1/templates 获取模板列表
GET /api/v1/templates/{id} 获取模板详情
PUT /api/v1/templates/{id} 更新模板
DELETE /api/v1/templates/{id} 删除模板
POST /api/v1/templates/{id}/publish 发布模板
POST /api/v1/templates/{id}/duplicate 复制模板

7.2 来源文件定义 API

方法 路径 说明
POST /api/v1/templates/{templateId}/source-files 添加来源文件定义
GET /api/v1/templates/{templateId}/source-files 获取来源文件定义列表
PUT /api/v1/templates/{templateId}/source-files/{id} 更新来源文件定义
DELETE /api/v1/templates/{templateId}/source-files/{id} 删除来源文件定义
POST /api/v1/templates/{templateId}/source-files/reorder 调整顺序

7.3 变量 API

方法 路径 说明
POST /api/v1/templates/{templateId}/variables 创建变量
GET /api/v1/templates/{templateId}/variables 获取变量列表
GET /api/v1/templates/{templateId}/variables/{id} 获取变量详情
PUT /api/v1/templates/{templateId}/variables/{id} 更新变量
DELETE /api/v1/templates/{templateId}/variables/{id} 删除变量
POST /api/v1/templates/{templateId}/variables/{id}/preview 预览提取结果

7.4 生成任务 API

方法 路径 说明
POST /api/v1/generations 创建生成任务
GET /api/v1/generations 获取生成任务列表
GET /api/v1/generations/{id} 获取任务详情
POST /api/v1/generations/{id}/execute 执行提取
GET /api/v1/generations/{id}/progress 获取执行进度
PUT /api/v1/generations/{id}/variables/{varName} 修改变量值
POST /api/v1/generations/{id}/confirm 确认并生成文档
GET /api/v1/generations/{id}/download 下载生成的文档

八、核心流程

8.1 创建模板流程

1. 用户上传示例报告
   POST /api/v1/parse/upload
   → 返回 document_id
   
2. 创建模板
   POST /api/v1/templates
   {
     "name": "110kV输变电工程预评价模板",
     "baseDocumentId": "doc_001"
   }
   → 返回 template_id

3. 添加来源文件定义
   POST /api/v1/templates/{templateId}/source-files
   {
     "alias": "可研批复",
     "description": "可研批复文件",
     "fileTypes": ["pdf", "docx"],
     "required": true,
     "exampleDocumentId": "doc_002"
   }

4. 创建变量(前端在编辑器中操作,调用此API)
   POST /api/v1/templates/{templateId}/variables
   {
     "name": "project_name",
     "displayName": "工程名称",
     "location": {
       "elementId": "elem_001",
       "type": "text",
       "startOffset": 10,
       "endOffset": 35
     },
     "exampleValue": "襄阳连云 110kV 输变电工程",
     "sourceFileAlias": "可研批复",
     "sourceType": "document",
     "sourceConfig": { ... },
     "extractType": "ai_extract",
     "extractConfig": { ... }
   }

5. 发布模板
   POST /api/v1/templates/{templateId}/publish

8.2 生成报告流程

1. 创建生成任务
   POST /api/v1/generations
   {
     "templateId": "tpl_001",
     "name": "武汉东湖110kV预评价",
     "sourceFileMap": {
       "可研批复": "doc_123",
       "站址报告": "doc_456"
     }
   }
   → 返回 generation_id

2. 执行提取
   POST /api/v1/generations/{generationId}/execute
   
3. 查询进度
   GET /api/v1/generations/{generationId}/progress
   → { "total": 10, "completed": 6, "currentVariable": "geology_summary" }

4. 查看提取结果,可修改
   GET /api/v1/generations/{generationId}
   PUT /api/v1/generations/{generationId}/variables/project_name
   { "value": "修正后的值" }

5. 确认并生成文档
   POST /api/v1/generations/{generationId}/confirm
   
6. 下载
   GET /api/v1/generations/{generationId}/download

九、与现有系统集成

9.1 复用已有服务

已有服务 复用内容
document-service 文档存储、DocumentElement 结构
parse-service 文档解析、结构化提取
ai-service DeepSeek API 调用、AI 提取
graph-service 可选:将变量注册为数据源

9.2 重构 extract-service

现有 extract-service 的代码需要重构:

原概念 新概念 说明
Project Template 模板取代项目
SourceDocument SourceFile 来源文件定义,不是具体文件
ExtractRule Variable 变量,绑定到文档位置
ExtractResult Generation.variable_values 生成任务中的变量值
- Generation 新增:生成任务

十、未来扩展

10.1 模板市场

  • 用户可将模板设为公开
  • 其他用户可基于公开模板创建自己的模板
  • 模板评分和使用统计

10.2 批量生成

  • 上传多组来源文件
  • 一次生成多份报告
  • 生成任务队列管理

10.3 版本控制

  • 模板版本管理
  • 生成任务关联模板版本
  • 版本对比和回滚

文档结束