将网络爬虫数据连接到RAG的实用指南
"我们想要制作一个能够以我们公司的数据作出回答的AI聊天机器人。" — 最近我们听到了这样的请求很多次。ChatGPT可能很聪明,但是要让它根据我们公司独有的最新数据来回答问题,就需要RAG。而RAG的性能最终取决于数据质量。
本文将总结使用网络爬虫收集的数据连接到RAG管道的整个过程,并附上实际代码。
目录
- RAG是什么?
- 整体管道流程
- 步骤1:爬取 — 收集原始数据
- 步骤2:分块 — 将文本分割为适当大小的块
- 步骤3:嵌入 + 存储向量数据库
- 步骤4:RAG查询 — 向LLM提问
- 数据质量决定RAG性能
- HashScraper MCP + LangChain集成
- 结束语
RAG是什么?
RAG(检索增强生成)简单来说是"检索 + 生成"。
在LLM生成答案之前,它会首先从外部数据库中检索相关文档并提供上下文。这样,GPT可以利用最新信息、内部文档和领域特定数据,大大减少幻觉(hallucination)的发生。
关键在于:LLM很聪明,但不知道的东西就是不知道。 RAG是一种通过搜索来补充LLM所不知道的内容的结构。
整体管道流程
RAG管道的整体流程分为5个阶段:
웹 크롤링 → 텍스트 청킹 → 임베딩 변환 → 벡터DB 저장 → LLM 쿼리
让我们逐步查看每个阶段的代码。
步骤1:爬取 — 收集原始数据
RAG的起点是数据。从网络上收集的产品信息、新闻、技术文档、社区帖子等都可以成为RAG的信息源。
这里重要的是进行干净的文本提取。如果将包含HTML标记、广告和导航菜单的数据直接输入,RAG的性能会大幅下降。
import requests
from bs4 import BeautifulSoup
def crawl_page(url):
"""단순 크롤링 예시 — 실전에서는 봇 차단, JS 렌더링 등 고려 필요"""
response = requests.get(url, headers={
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64)"
})
soup = BeautifulSoup(response.text, "html.parser")
# 본문 텍스트만 추출 (네비게이션, 광고 등 제거)
for tag in soup(["nav", "header", "footer", "script", "style", "aside"]):
tag.decompose()
text = soup.get_text(separator="\n", strip=True)
return text
但是现实并不那么简单。对于使用JavaScript进行渲染的SPA、需要登录的页面、被机器人阻止的网站,仅使用requests可能会有限制。
步骤2:分块 — 将文本分割为适当大小的块
如果将整个文档嵌入,搜索准确性会降低。将文本分割为适当大小的块是关键。
from langchain_text_splitters import RecursiveCharacterTextSplitter
splitter = RecursiveCharacterTextSplitter(
chunk_size=500, # 청크당 최대 500자
chunk_overlap=50, # 청크 간 50자 겹침 (문맥 유지)
separators=["\n\n", "\n", ". ", " "] # 분할 우선순위
)
documents = splitter.split_text(crawled_text)
print(f"총 {len(documents)}개 청크 생성")
分块提示:
- 如果块太小,上下文会中断;如果太大,搜索准确性会降低
- 对于韩文文本,通常使用500~800个字符的块可以获得良好的性能
- 设置chunk_overlap以防止句子被切断
步骤3:嵌入 + 存储向量数据库
将块转换为向量(数字数组),并将其存储在向量数据库中。这里使用OpenAI嵌入 + ChromaDB组合。
from langchain_openai import OpenAIEmbeddings
from langchain_chroma import Chroma
# 임베딩 모델 초기화
embeddings = OpenAIEmbeddings(model="text-embedding-3-small")
# 벡터DB에 저장
vectorstore = Chroma.from_texts(
texts=documents,
embedding=embeddings,
collection_name="crawled_data",
persist_directory="./chroma_db"
)
print(f"{len(documents)}개 청크를 벡터DB에 저장 완료")
其他向量数据库(如Pinecone、Weaviate、Qdrant等)也可以在LangChain中使用相同的接口。
步骤4:RAG查询 — 向LLM提问
现在当用户提出问题时,从向量数据库中检索相关文档并将上下文传递给LLM。
from langchain_openai import ChatOpenAI
from langchain.chains import RetrievalQA
# LLM 설정
llm = ChatOpenAI(model="gpt-4o", temperature=0)
# RAG 체인 구성
qa_chain = RetrievalQA.from_chain_type(
llm=llm,
chain_type="stuff",
retriever=vectorstore.as_retriever(search_kwargs={"k": 3})
)
# 질문하기
answer = qa_chain.invoke("이 제품의 최신 가격은 얼마인가요?")
print(answer["result"])
注意:
RetrievalQA是LangChain的传统Chain接口。在最新版本中,推荐使用基于LangGraph的RAG配置,但为了理解概念,我们使用最直观的方法来解释。
这就是RAG的整体流程。爬取 → 分块 → 嵌入 → 向量数据库 → LLM查询。结构本身很简单。
数据质量决定RAG性能
RAG中最容易被低估的部分是输入数据的质量。
即使使用了优秀的嵌入模型和LLM,如果输入数据混乱,结果也会混乱。实际上,RAG性能问题的大部分源于数据问题,而不是模型。
常见的数据质量问题:
- 导航、侧边栏文本与正文混合 → 搜索时产生噪音
- 不完整的爬取(JS渲染失败) → 重要信息丢失
- 重复数据 → 搜索结果偏向
- 编码错误、特殊字符问题 → 嵌入质量下降
垃圾进,垃圾出。 在爬取阶段获取干净的数据将决定RAG管道的成功与否。
HashScraper MCP + LangChain集成
如果自己编写爬虫,会花费时间处理机器人阻止、JS渲染、代理管理等附加问题。使用HashScraper的MCP(Model Context Protocol)服务器,您可以专注于RAG管道而无需担心爬取基础设施。
# 해시스크래퍼 MCP를 LangChain Document Loader로 활용하는 예시
from langchain_core.documents import Document
from langchain_text_splitters import RecursiveCharacterTextSplitter
from langchain_chroma import Chroma
from langchain_openai import OpenAIEmbeddings
# 해시스크래퍼 API로 데이터 수집 — 봇 차단 사이트도 OK
import requests
response = requests.post(
"https://api.hashscraper.com/api/scrape",
json={
"url": "https://target-site.com/products",
"format": "markdown" # markdown 또는 text
},
headers={
"X-API-Key": "YOUR_API_KEY",
"Content-Type": "application/json; version=2"
}
).json()
# LangChain Document로 변환
docs = [
Document(
page_content=response["data"]["content"],
metadata={
"url": response["data"]["url"],
"title": response["data"]["title"]
}
)
]
# 이후는 동일: 청킹 → 임베딩 → 벡터DB → RAG
embeddings = OpenAIEmbeddings(model="text-embedding-3-small")
splitter = RecursiveCharacterTextSplitter(chunk_size=500, chunk_overlap=50)
chunks = splitter.split_documents(docs)
vectorstore = Chroma.from_documents(chunks, embeddings)
将HashScraper用作RAG数据源的原因:
- 即使在机器人阻止网站上,也可以稳定地提取干净文本
- 自动处理JavaScript渲染、登录流程
- 内置代理管理、IP轮换 — 无需担心基础设施
- 结构化的数据输出 → 提高分块/嵌入质量
结束语
RAG管道在结构上很简单。但在实践中,决定性能的最终是第一阶段的数据收集质量。
与其花时间编写和维护爬虫,不如在经过验证的爬取基础设施上专注于RAG逻辑,这可能是更有效的选择。
如果您需要构建基于爬取数据的RAG管道,请在HashScraper上咨询。我们将根据实际经验帮助您从数据收集到AI集成。




