在构建企业RAG知识库时,数据源通常可分为两类:
-
企业内部知识库:结构明确、数据量中等、可控性强;
-
行业领域专属数据源:数据公开但体量庞大,结构复杂。
企业内部数据与行业数据的结合,是构建高质量AI问答系统的核心路径。本篇文章聚焦于企业财报类RAG系统的数据采集阶段,以巨潮资讯网为例,介绍一个稳定、高效的爬虫系统设计方案。

一、为什么选择巨潮资讯网?
巨潮资讯网是中国证监会指定的信息披露平台,覆盖沪深两市全部上市公司的公告,具有如下优势:
-
权威性:信息来源可信;
-
规范性:公告类型明确、字段标准统一;
-
结构清晰:适合自动解析与结构化处理;
-
接口稳定:页面变动较少,易于长期维护;
-
低反爬压力:目前基本无复杂的反爬虫机制,适合批量抓取。
这些特性使其成为构建金融类问答知识库的首选数据源。
二、爬虫系统设计
该爬虫采用模块化设计与高容错能力,支持如下关键能力:
-
行业维度的全量遍历
-
动态页数判断
-
下载断点续传
-
文件自动去重
核心模块结构(Python实现)
爬虫围绕 CninfoSpider
类构建,划分为以下四个功能模块:
1. 下载路径与记录管理
self.download_dir = Path("cninfo_pdfs")
self.download_log = self.download_dir / "download_log.txt"
-
按“行业 ➝ 股票代码”层级保存PDF
-
每次下载写入日志,避免重复
2. 公告请求与参数构造
def get_announcements(self, page_num=1, category='category_ndbg_szsh', trade='制造业', ...)
-
自动构建POST参数(公告分类、行业、时间段等)
-
模拟浏览器请求,支持翻页与失败重试机制
3. PDF下载与异常处理
def download_pdf(self, pdf_url, trade_name, stock_code, filename)
-
判断文件是否已下载
-
下载后按行业+股票代码归档
-
若文件为空或异常,自动删除并标记失败
4. 全行业动态遍历
def run_all_industries_dynamic(...)
-
遍历官方19个一级行业
-
动态计算页数,防止漏采或重复采集
-
可设置请求延迟,降低被封风险
三、运行示例与目录结构
运行主函数即可拉取指定时间范围内的全行业年报:
if __name__ == "__main__":
spider = CninfoSpider()
spider.run_all_industries_dynamic(
start_page=1,
delay=1,
category='category_ndbg_szsh',
se_date='2025-01-01~2025-07-20' )
输出示例:
开始按行业分类爬取巨潮资讯网公告PDF
共19个行业分类
正在处理第1/19个行业: 农、林、牧、渔业
行业 '农、林、牧、渔业' 共有 138 条记录,总计 5 页
第1页找到 6 个PDF文件...
下载完成: cninfo_pdfs/农、林、牧、渔业/002123/2025年年度报告.pdf
最终文件结构示例:
cninfo_pdfs/
├──制造业/
│─
──600519/
│─
─
──
2025年年度报告.pdf
└──金融业/
└──
─000001/
└──
─
─2025年年度报告.pdf
目前2024年上市公司年报数据的总量约为 13GB PDF 文件,已具备构建金融问答知识库的基础。
四、与RAG系统的集成流程
数据采集是RAG系统的第一步,典型流程如下图所示:
数据获取(爬虫)
-
批量下载PDF,记录元数据
内容解析
-
OCR识别(如 PaddleOCR)
-
PDF结构解析(如 MinerU)
向量化建库
-
文本分块
-
向量生成(如 BGE)
-
存入向量数据库(如 Elasticsearch / Milvus)
检索增强生成(RAG)
-
用户查询向量数据库
-
调用LLM生成结合原文的精准回答