# LangChain 内置文档加载器使用技巧
LangChain 内部封装了大量不同类型的文档加载器,用于把各种来源的数据统一转换成 Document。常见类型包括 CSV、目录、HTML 网页、JSON、Markdown、PDF、Office 文档以及通用文件等。
不同加载器的使用流程大体一致:
- 根据文件路径、URL 或配置参数创建加载器实例。
- 调用
load()或lazy_load()得到 Document。 - 检查
page_content与metadata。 - 再进入清洗、切分、向量化和入库流程。
差异主要体现在两个地方:一是实例化时传入的参数不同;二是返回的 Document 内容和 metadata 结构不同。例如 CSV 加载器可以指定列,DirectoryLoader 需要目录路径和文件匹配规则,JSONLoader 需要知道 JSON 中要抽取的结构。

# Markdown 文档加载器
Markdown 是常见的轻量级文本格式,很多 API 文档、产品说明、内部知识库都可以用 Markdown 保存。
LangChain 中可以使用 UnstructuredMarkdownLoader 加载 Markdown 文件。使用该加载器前,需要安装 unstructured:
pip install unstructured
示例代码:
from langchain_community.document_loaders import UnstructuredMarkdownLoader
loader = UnstructuredMarkdownLoader("./项目API资料.md")
documents = loader.load()
print(documents)
print(len(documents))
print(documents[0].metadata)
2
3
4
5
6
7
8
默认情况下,Markdown 文件通常会被加载为 Document 列表。后续可以继续使用文本分割器切分成更适合检索的 chunk。
如果希望按 Markdown 元素进行拆分,可以使用 mode="elements":
from langchain_community.document_loaders import UnstructuredMarkdownLoader
loader = UnstructuredMarkdownLoader("./项目API资料.md", mode="elements")
documents = loader.load()
for document in documents:
print(document.page_content)
print(document.metadata)
2
3
4
5
6
7
8
mode="elements" 更适合保留标题、段落等结构,但它不是最终的 chunk 策略。入库前仍然要根据内容长度和检索需求决定是否继续切分。
# Office 文档加载器
Office 文件不是普通文本文件,不能直接用 TextLoader 读取。Excel、Word、PPT 都需要对应的加载器处理。
示例代码:
from langchain_community.document_loaders import (
UnstructuredPowerPointLoader,
)
# excel_loader = UnstructuredExcelLoader("./员工考勤表.xlsx", mode="elements")
# excel_documents = excel_loader.load()
# word_loader = UnstructuredWordDocumentLoader("./喵喵.docx")
# documents = word_loader.load()
ppt_loader = UnstructuredPowerPointLoader("./章节介绍.pptx")
documents = ppt_loader.load()
print(documents)
print(len(documents))
print(documents[0].metadata)
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
Office 文档解析时要重点关注结构是否丢失。比如 Excel 的表格行列、PPT 的页面结构、Word 的标题层级,如果被解析成一大段无结构文本,后续检索效果会明显下降。
# URL 网页加载器
网页内容可以使用 WebBaseLoader 加载:
from langchain_community.document_loaders import WebBaseLoader
loader = WebBaseLoader("https://imooc.com")
documents = loader.load()
print(documents)
print(len(documents))
print(documents[0].metadata)
2
3
4
5
6
7
8
网页加载器适合快速把 URL 页面变成 Document,但网页通常包含导航、页脚、广告、登录入口、推荐位、重复链接等噪声。真实入库前,通常还需要做清洗:
- 去掉导航和页脚。
- 去掉重复链接和按钮文字。
- 去掉空白行、Tab 和无意义换行。
- 保留页面 URL、标题、发布时间等 metadata。
如果页面依赖前端动态渲染,普通网页加载器可能拿不到完整内容,需要考虑浏览器渲染类抓取工具或专门的网页解析服务。
# 通用文件加载器
当不确定文件类型,或者想快速验证不同文件的读取效果时,可以使用 UnstructuredFileLoader:
from langchain_community.document_loaders import UnstructuredFileLoader
loader = UnstructuredFileLoader("./项目API资料.md")
documents = loader.load()
print(documents)
print(len(documents))
print(documents[0].metadata)
2
3
4
5
6
7
8
通用文件加载器的优势是覆盖面广,适合作为兜底方案;缺点是对特定格式的结构保留不一定最好。能明确文件类型时,优先使用专用加载器。
# 加载器选型
| 数据源 | 推荐加载器 | 注意点 |
|---|---|---|
| 纯文本、源码、日志 | TextLoader | 需要指定正确编码 |
| Markdown | UnstructuredMarkdownLoader | 可按元素解析,但仍要评估 chunk 粒度 |
| Excel | UnstructuredExcelLoader | 关注表格结构是否保留 |
| Word | UnstructuredWordDocumentLoader | 关注标题层级、段落、页码 |
| PPT | UnstructuredPowerPointLoader | 关注每页内容和备注 |
| HTML 文件 | UnstructuredHTMLLoader、BSHTMLLoader | 需要清洗噪声 |
| 网页 URL | WebBaseLoader 或网页解析服务 | 动态页面可能抓不全 |
PyPDFLoader、UnstructuredPDFLoader、其他 PDF 解析器 | 关注页码、表格、图片文字 | |
| 不确定类型 | UnstructuredFileLoader | 适合兜底,不一定保留最佳结构 |
# 最新版 LangChain 用法提示
最新版 LangChain 仍然保留“文档加载器输出 Document”的整体思路。官方文档中也强调,Document loaders 提供标准接口,把不同来源的数据读入 Document 格式。
需要注意几点:
load()和lazy_load()仍然是文档加载器的通用接口。- 大文件或大批量数据更推荐
lazy_load(),不要一次性把所有内容读进内存。 - 社区加载器通常来自
langchain_community或对应集成包,使用前要确认依赖是否安装。 load_and_split()不优先作为新代码主路径,建议加载后显式调用分割器。- 对于 PDF、网页等复杂数据,最新版生态中也有 Docling、Unstructured 等不同解析方案,生产中要用样本对比解析质量。
推荐写法:
from langchain_community.document_loaders import UnstructuredMarkdownLoader
from langchain_text_splitters import RecursiveCharacterTextSplitter
loader = UnstructuredMarkdownLoader("./项目API资料.md")
documents = loader.load()
splitter = RecursiveCharacterTextSplitter(
chunk_size=1000,
chunk_overlap=200,
add_start_index=True,
)
chunks = splitter.split_documents(documents)
2
3
4
5
6
7
8
9
10
11
12
# 拓展
内置加载器只能解决常见格式。如果数据来自数据库、内部 API、对象存储、权限系统或业务平台,就需要自定义 Loader 或在 Loader 外层做适配。
另外,加载器只解决“读出来”的问题,不保证“适合检索”。入库前还要检查:
- 正文是否完整。
- 是否有乱码。
- metadata 是否保留来源。
- 表格和标题是否丢失。
- 是否存在大量重复和无效内容。
# 常见问题
# 为什么专用 Loader 优先于通用 Loader?
专用 Loader 更了解文件结构,更容易保留页码、标题、表格、段落等信息。通用 Loader 覆盖面广,但结构保留不一定稳定。
# mode="elements" 是不是就不用切分了?
不是。mode="elements" 是解析阶段按元素拆分,最终是否适合作为 chunk,还要看长度、语义完整性和检索效果。
# 网页加载后为什么检索结果很差?
很多网页正文里混入导航、页脚、广告、推荐链接和版权信息。如果不清洗,这些噪声会进入向量库,导致召回质量下降。
# 面试题
# 文档加载器在 RAG 中解决什么问题?
它负责把不同来源的数据统一转换成 Document,从而让后续分割、向量化、检索都面向同一种数据结构。
# 如何选择内置 Loader?
先看数据源类型,能确定格式就选专用 Loader;不能确定格式或只是快速验证,可以用通用 Loader 兜底。选完后必须抽样检查正文和 metadata。
# 为什么 Loader 不应该负责向量化?
Loader 的职责是读取并转换成 Document。向量化属于索引阶段。如果混在一起,数据读取问题和索引问题会耦合,后续很难排查。
# 生产问题排查
| 问题 | 常见原因 | 处理方式 |
|---|---|---|
| 加载失败 | 依赖包没装、路径错误、文件格式不支持 | 安装对应依赖,检查路径和 Loader 类型 |
| 内容乱码 | 编码不匹配 | 显式指定 encoding 或换解析器 |
| metadata 太少 | 通用 Loader 保留信息有限 | 使用专用 Loader 或手动补字段 |
| 网页噪声多 | 导航、页脚、广告进入正文 | 增加清洗规则 |
| Office 表格丢失 | 解析器不适合该文件 | 对比不同 Loader,必要时专门解析表格 |
| 批量导入内存高 | 使用 load() 一次性加载 | 改用 lazy_load() 或队列处理 |