import logging import time from langchain_openai import ChatOpenAI from langchain_core.prompts import ChatPromptTemplate from typing import List, Dict, Any import json from config.settings import LLM_MODEL, LLM_API_KEY, LLM_BASE_URL, LLM_TEMPERATURE, LLM_TIMEOUT from parser.base_parser import BaseParser class WorkFaceParser(BaseParser): def __init__(self): super().__init__() self.llm = ChatOpenAI( model=LLM_MODEL, api_key=LLM_API_KEY, base_url=LLM_BASE_URL, temperature=LLM_TEMPERATURE, timeout=LLM_TIMEOUT ) def parse(self, file_path: str) -> Dict[str, Any]: documents = self.load_pdf(file_path) full_text = "\n".join([doc.page_content for doc in documents]) return self._parse(full_text) def _parse(self, text: str) -> Dict[str, Any]: start_time = time.time() prompt = ChatPromptTemplate.from_messages([ ("system", ''' 你是专业煤矿工作面作业规程解析助手。 请从文档中一次性提取所有指定信息,**严格仅输出标准JSON**,禁止输出任何多余文字、解释、前言后语。 固定JSON字段键名: working_face_name 工作面名称 max_control_distance 中间架最大控顶距离(单位米) min_control_distance 中间架最小控顶距离(单位米) face_length 工作面切眼长度(单位米) avg_mining_height 平均采高(单位米) avg_section_area 工作面平均断面(单位平方米) 填充规则: 1. 文本无对应数据时,字符串填空文本"",数值统一填0,严禁使用null 2. 数值只提取纯数字,自动剔除米、m等单位 3. 必须严格按照上述英文键名输出,字段顺序不可更改 4. 最终只返回纯净JSON格式,无任何额外内容 输出示例 {{ "working_face_name": "xxxx工作面", "max_control_distance": 0, "min_control_distance": 0, "face_length": 0, "avg_mining_height": 0, "avg_section_area": 0 }} '''), ("human", "请解析以下煤矿工作面作业规程文档内容:\n{text}") ]) # 调用大模型(唯一一次) chain = prompt | self.llm response = chain.invoke({"text": text}) # 控制在安全长度内 elapsed_time = round(time.time() - start_time, 2) # 日志输出 print(f"文档解析完成| 总耗时: {elapsed_time} 秒") return json.loads(response.content) if __name__ == '__main__': parser = WorkFaceParser() result = parser.parse("C:\\Users\ky\Desktop\配风计划研判\布尔台\布尔台煤矿12204综采工作面作业规程doc. -0507.pdf") print(json.dumps(result, ensure_ascii=False, indent=2))