You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

分页页面PDF链接截图获取问题及技术方案咨询

问题解答

1. 为什么requests+BeautifulSoup能拿到所有链接,Selenium却不行?

核心差异在于页面渲染逻辑和AJAX的作用:

  • requests是直接向服务器发起HTTP请求,拿到的是服务器返回的完整HTML源码——这个页面的服务器大概率把所有864个PDF链接提前嵌入到了返回的HTML里,所以BeautifulSoup直接解析就能获取全量内容。
  • Selenium是模拟真实浏览器加载页面,而该页面的分页采用了AJAX动态加载机制:初始加载时,浏览器只渲染第一页的内容,剩余分页的数据不会自动加载。只有当你点击分页按钮时,浏览器才会在不刷新整个页面的前提下,偷偷发送AJAX请求到服务器获取对应页的数据,再通过JavaScript把新内容渲染到页面中。此时你直接用Selenium查找后续分页的元素,这些元素还未被添加到页面的DOM(文档对象模型)里,自然会抛出NoSuchElementException。

简单总结:requests拿的是服务器给出的「全量数据包」,Selenium拿的是浏览器「逐步加载的内容片段」。

2. 除点击分页外的通用解决方案

推荐两种更高效的思路:

方案一:复用requests的全量数据生成本地页面

既然requests已经能获取所有PDF链接,你可以把这些链接整理成一个简易HTML页面,保存为本地文件后用Selenium打开。此时所有元素都在DOM中,直接定位截图即可,完全不用处理分页逻辑。

示例代码思路:

import requests
from bs4 import BeautifulSoup
from selenium import webdriver
from selenium.webdriver.common.by import By

# 用requests抓取所有PDF链接
url = "https://aplng.com.au/document-library/"
response = requests.get(url)
soup = BeautifulSoup(response.text, "html.parser")
pdf_links = soup.find_all("a", href=lambda x: x and x.endswith(".pdf"))

# 生成包含所有链接的本地HTML
html_content = """
<!DOCTYPE html>
<html>
<body>
"""
for link in pdf_links:
    html_content += f'<div class="pdf-item"><a href="{link["href"]}">{link.text.strip()}</a></div>\n'
html_content += """
</body>
</html>
"""
with open("all_pdfs.html", "w", encoding="utf-8") as f:
    f.write(html_content)

# Selenium打开本地页面并截图
driver = webdriver.Chrome()
driver.get("file:///你的本地文件路径/all_pdfs.html")
# 定位所有PDF链接区域并逐个截图
pdf_elements = driver.find_elements(By.CLASS_NAME, "pdf-item")
for idx, elem in enumerate(pdf_elements):
    elem.screenshot(f"pdf_area_{idx}.png")
driver.quit()

方案二:直接调用页面的API接口

打开浏览器开发者工具(按F12),切换到「网络」标签,点击分页按钮观察浏览器发送的请求——你会发现一个专门加载文档列表的API(通常是GET请求,参数包含页码、每页数量)。直接请求这个API就能拿到所有分页的JSON数据,再根据数据生成页面或直接定位元素截图,比模拟点击效率高得多。

3. 若必须点击分页,如何规避异常?

如果一定要模拟分页点击,重点解决元素等待和分页终止判断的问题:

  • 用显式等待替代固定延迟:不要用time.sleep()这种生硬的等待,改用WebDriverWait配合expected_conditions等待元素加载完成,比如等待下一页按钮可见、等待当前页的PDF元素出现。
    示例代码:
    from selenium.webdriver.support.ui import WebDriverWait
    from selenium.webdriver.support import expected_conditions as EC
    from selenium.webdriver.common.by import By
    
    wait = WebDriverWait(driver, 10)
    # 等待下一页按钮可见
    next_btn = wait.until(EC.visibility_of_element_located((By.CSS_SELECTOR, "你的下一页按钮选择器")))
    next_btn.click()
    # 等待当前页的PDF元素加载完成
    wait.until(EC.presence_of_all_elements_located((By.CSS_SELECTOR, "你的PDF链接选择器")))
    
  • 判断分页终止条件:当页面没有下一页按钮(比如按钮变灰、消失)时停止点击。可以用try-except捕获NoSuchElementException来判断是否到达最后一页。
  • 处理元素交互问题:如果分页按钮被页面元素遮挡,用driver.execute_script("arguments[0].scrollIntoView();", next_btn)滚动到按钮位置再点击;如果点击无反应,尝试用JS执行点击:driver.execute_script("arguments[0].click();", next_btn)。
  • 添加异常重试机制:偶尔会因网络波动导致元素加载失败,给点击和定位逻辑加重试次数,比如循环3次尝试点击下一页。

内容的提问来源于stack exchange,提问作者Fariz Awi

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.06 09:40:32