Python爬虫翻页案例:从入门到精通,6种高效翻页策略实战详解
目录导读
- 翻页爬取的核心逻辑
- 常见翻页模式与识别技巧
- 基于URL参数的翻页(静态翻页)
- 基于AJAX请求的翻页(动态翻页)
- 模拟点击“加载更多”按钮翻页
- 处理分页中的JavaScript滚动翻页
- 翻页爬虫的常见错误与解决方法
- SEO优化与反爬策略应对
- 问答专区
- 总结与最佳实践
翻页爬取的核心逻辑
在Web数据抓取中,翻页是最常见的需求之一,无论你是抓取电商商品列表、新闻列表还是论坛帖子,几乎所有分页数据都需要通过翻页逻辑来完整获取。

核心流程:
- 分析目标网站的分页机制(URL参数、POST请求、AJAX加载、滚动加载等)
- 构造翻页请求(拼接URL、传递参数、处理cookie)
- 解析每一页的HTML/JSON数据
- 循环执行直到最后一页或满足停止条件
与单页爬虫相比,翻页爬虫需要额外处理页数控制、请求间隔、去重和异常重试。
常见翻页模式与识别技巧
| 类型 | 特征 | 示例 |
|---|---|---|
| URL参数翻页 | page=1, page=2 ... | 博客列表、新闻网站 |
| 表单POST翻页 | 提交page参数到后端 | 一些B2B平台 |
| AJAX动态加载 | 请求JSON数据,前端渲染 | 电商商品列表(API) |
| “加载更多”按钮 | 点击后追加内容 | 社交媒体、评论区 |
| 滚动无限加载 | 监听滚动事件,动态追加 | 知乎、微博 |
| JavaScript分页组件 | 复杂前端框架实现的分页 | 后台管理系统 |
识别技巧:
- 打开开发者工具(F12)→ 网络(Network)选项卡
- 点击翻页按钮,观察请求列表
- 查看是XHR请求(AJAX)还是文档(Document)请求
- 提取URL或请求体中的page/offset参数
案例一:基于URL参数的翻页(静态翻页)
这是最简单、最常见的翻页模式,以抓取某个新闻网站为例,URL模式为:
https://example.com/news?page=1
Python代码示例:
import requests
from bs4 import BeautifulSoup
import time
def crawl_news(base_url, max_pages=10):
headers = {
'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36'
}
all_articles = []
for page in range(1, max_pages + 1):
url = f"{base_url}?page={page}"
try:
response = requests.get(url, headers=headers, timeout=10)
response.raise_for_status()
soup = BeautifulSoup(response.text, 'html.parser')
# 提取文章列表(根据实际网站调整选择器)
articles = soup.select('.article-item .title a')
for a in articles:
all_articles.append({
'title': a.get_text(strip=True),
'link': a['href']
})
print(f"第{page}页完成,获取到{len(articles)}篇文章")
time.sleep(1) # 礼貌性延时
except Exception as e:
print(f"第{page}页出错: {e}")
continue
return all_articles
关键点:
- 使用f-string动态拼接URL
- 设置
time.sleep()避免请求过快被封 - 使用
try-except处理网络异常
案例二:基于AJAX请求的翻页(动态翻页)
现代网站常通过AJAX加载数据,打开开发者工具 → Network → XHR,找到返回JSON的请求。
识别特征:请求返回的不是HTML,而是JSON格式的数据。
示例代码(抓取某电商API):
import requests
import json
def scrape_product_api(api_url, total_pages=20):
headers = {
'User-Agent': 'Mozilla/5.0',
'Accept': 'application/json',
'Referer': 'https://example.com/'
}
products = []
for page in range(1, total_pages + 1):
params = {
'page': page,
'size': 20,
'sort': 'price_asc'
}
try:
response = requests.get(api_url, headers=headers, params=params, timeout=10)
data = response.json()
# 假设数据在data['items']中
for item in data.get('items', []):
products.append({
'id': item['id'],
'name': item['name'],
'price': item['price']
})
# 检查是否还有下一页(根据返回的总页数判断)
if page >= data.get('totalPages', total_pages):
break
print(f"API第{page}页完成")
time.sleep(0.5)
except Exception as e:
print(f"获取第{page}页失败: {e}")
continue
return products
注意事项:
- 需要模拟Referer和Cookies,特别是需要登录的网站
- 解析返回的JSON结构,找到总页数、总记录数等终止条件
- 注意分页参数可能是
offset、pageNo、start等不同命名
案例三:模拟点击“加载更多”按钮翻页
有些网站使用“加载更多”按钮,需要发送POST请求或使用Selenium模拟点击。
使用Selenium方案:
from selenium import webdriver
from selenium.webdriver.common.by import By
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC
import time
def scrape_load_more(url, max_clicks=50):
driver = webdriver.Chrome()
driver.get(url)
all_items = []
click_count = 0
while True:
# 等待内容加载
WebDriverWait(driver, 10).until(
EC.presence_of_element_located((By.CSS_SELECTOR, '.item'))
)
# 提取当前可见的所有项
items = driver.find_elements(By.CSS_SELECTOR, '.item')
for item in items:
text = item.text
if text not in all_items: # 去重
all_items.append(text)
# 查找“加载更多”按钮
try:
load_more_btn = driver.find_element(By.CSS_SELECTOR, '.load-more-btn')
if load_more_btn.is_displayed():
load_more_btn.click()
click_count += 1
print(f"已点击{click_count}次,获取到{len(all_items)}条数据")
time.sleep(2) # 等待新内容加载
else:
break
except:
print("没有更多按钮,结束")
break
# 安全限制,防止无限循环
if click_count >= max_clicks:
break
driver.quit()
return all_items
优缺点分析:
- 优点:能处理复杂的前端交互
- 缺点:速度慢,消耗资源,容易被反爬
案例四:处理分页中的JavaScript滚动翻页
无限滚动翻页需要模拟滚动行为。
from selenium import webdriver
from selenium.webdriver.common.by import By
import time
def scrape_infinite_scroll(url, max_scrolls=30):
driver = webdriver.Chrome()
driver.get(url)
last_height = driver.execute_script("return document.body.scrollHeight")
scroll_count = 0
all_data = []
while True:
# 滚动到底部
driver.execute_script("window.scrollTo(0, document.body.scrollHeight);")
time.sleep(2) # 等待数据加载
# 计算新高度
new_height = driver.execute_script("return document.body.scrollHeight")
if new_height == last_height:
print("已滚动到底部")
break
last_height = new_height
scroll_count += 1
# 提取新加载的数据(示例选择器)
items = driver.find_elements(By.CSS_SELECTOR, '.post-item')
for item in items:
title = item.find_element(By.CSS_SELECTOR, '.title').text
all_data.append(title)
print(f"已滚动{scroll_count}次,获取到{len(all_data)}条数据")
if scroll_count >= max_scrolls:
break
driver.quit()
return list(set(all_data)) # 去重
优化建议:
- 使用
WebDriverWait等待特定元素出现,替代固定时间 - 检测页面底部是否有“加载完成”标志
翻页爬虫的常见错误与解决方法
| 错误类型 | 现象 | 解决方案 |
|---|---|---|
| 参数错误 | 翻页后返回相同内容 | 检查分页参数是否正确、是否需要有数据 |
| 反爬拦截 | 出现验证码、503错误 | 添加User-Agent、Cookie、代理IP |
| 动态页面 | 无法获取渲染后内容 | 使用Selenium/Playwright渲染JS |
| 频率限制 | 请求被临时封禁 | 降低请求速率,使用随机延时 |
| 内存溢出 | 处理大量数据时崩溃 | 使用生成器、分批写入文件/数据库 |
| 编码问题 | 中文乱码 | 设置response.encoding='utf-8' |
调试技巧:
- 先用
curl或Postman测试单个请求 - 打印每次请求的URL和状态码
- 保存中间页面HTML用于分析
SEO优化与反爬策略应对
如何让爬虫更符合SEO规范?
- 尊重robots.txt:爬取前检查
https://example.com/robots.txt - 设置合理延时:建议1-3秒间隔,模拟人类浏览行为
- 标识爬虫身份:在User-Agent中添加公司名称或用途
- 避免重复请求:记录已爬取的URL,防止循环抓取
应对常见反爬措施
- IP限制:使用代理池(免费/付费代理轮换)
- Cookie验证:使用Session对象保持会话
- 验证码:接入打码平台或机器学习OCR
- 请求头校验:模拟完整的请求头(包括Referer、Origin)
问答专区
Q1:如何判断翻页是否到了最后一页?
A:检查返回数据是否为空,或返回的JSON中包含hasNext: false、totalPages字段,对于HTML页面,查找是否有“下一页”按钮的disabled属性或不存在。
Q2:翻页爬虫被IP封禁怎么办?
A:
- 降低请求速率(time.sleep(3-5))
- 使用代理IP池(推荐免费资源:爬虫代理、芝麻代理等)
- 添加随机User-Agent
- 改用Selenium模拟真实浏览器
Q3:遇到需要登录的翻页怎么办?
A:
- 手动登录后获取Cookie,在请求中携带
- 使用Selenium模拟登录,保存Session
- 针对API请求,查看是否需要Token或Authorization头部
Q4:动态加载的翻页数据如何解析更高效?
A:优先使用API接口,直接抓取JSON数据,比Selenium快10倍以上,通过浏览器开发者工具找到真实请求的URL和参数。
Q5:翻页爬取的数据怎么存储?
A:
- 小规模数据:CSV/Excel
- 中规模数据:SQLite/MongoDB
- 大规模数据:分布式存储 + MySQL + Redis缓存
总结与最佳实践
翻页爬取是Python爬虫的进阶技能,掌握不同翻页模式的识别和处理方法至关重要,以下是关键建议:
- 先分析,后编码:用浏览器开发者工具分析网络请求再动手
- 优先选择API:JSON接口比HTML解析稳定100倍
- 优雅地处理异常:设置重试机制,记录失败页码
- 尊重规则:设置合理延时,遵守robots.txt
- 代码模块化:将分页逻辑独立封装,便于复用和测试
- 数据去重:使用集合(Set)或数据库唯一索引避免重复
无论是基于URL参数的静态翻页,还是复杂的AJAX/滚动翻页,核心思想都是找到翻页规律 → 模拟请求 → 解析数据 → 循环处理,掌握了这些案例,你可以应对90%以上的翻页场景。
爬虫技术是一把双刃剑,请合法、合规地使用,不要对目标服务器造成过大压力。