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

如何用Selenium打开并抓取多个链接?循环异常问题求助

Selenium爬取OCR报纸文章的循环与文本获取问题

问题描述

我是Python爬虫新手,遇到了一个奇怪的问题。因数据源的代理设置,我选择用Selenium从URL列表中抓取经过OCR处理的报纸文章,但每次运行代码都会收到文本数据的回溯报错。使用.click()打开隐藏面板后,仅能获取到数据集中的最后一行;不使用该方法则所有行都为空,调整sleep设置也无效。更新后确认循环存在问题——我只能获取第一个或最后一个值,中间的都无法获取。

我的代码如下:

article_links = []
for link in driver.find_elements_by_xpath('/html/body/div[1]/main/section[1]/ul[2]/li[*]/div[2]/div[1]/h3/a'):
    links = link.get_attribute("href")
    article_links.append(links)

articles = []
for article in article_links:
    driver.switch_to.window(driver.window_handles[-1])
    driver.get(article)
    driver.find_element_by_css_selector("#js-doc-explorer-show-additional-views").click()
    time.sleep(1)
    for article_text in driver.find_elements_by_css_selector("#ocr-container > div.fulltext-ocr.js-page-ocr"):
        articles.append(article_text)

文本数据的Xpath:

/html/body/div[2]/main/section/div[2]/div[2]/section[2]/div/div[4]/text()

另外,是否可以获取每个链接的源码后用BeautifulSoup解析?


解决方案

1. 修复循环与文本获取问题

  • 移除不必要的窗口切换:你当前用driver.get(article)是在当前窗口加载新页面,driver.switch_to.window(driver.window_handles[-1])完全多余,删除这行即可避免窗口切换带来的干扰。
  • 获取实际文本内容:你现在把元素对象article_text添加到列表,而非文本内容,需要改为article_text.text或article_text.get_attribute('innerText')。
  • 替换固定sleep为显式等待:固定sleep不可靠,改用Selenium的显式等待确保元素加载完成,避免因渲染延迟导致的空数据:
    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
    
    article_links = []
    for link in driver.find_elements_by_xpath('/html/body/div[1]/main/section[1]/ul[2]/li[*]/div[2]/div[1]/h3/a'):
        links = link.get_attribute("href")
        article_links.append(links)
    
    articles = []
    for article in article_links:
        driver.get(article)
        # 等待并点击显示OCR面板
        WebDriverWait(driver, 10).until(
            EC.element_to_be_clickable((By.CSS_SELECTOR, "#js-doc-explorer-show-additional-views"))
        ).click()
        # 等待OCR文本容器加载完成
        ocr_elements = WebDriverWait(driver, 10).until(
            EC.presence_of_all_elements_located((By.CSS_SELECTOR, "#ocr-container > div.fulltext-ocr.js-page-ocr"))
        )
        # 提取文本并添加到列表
        for elem in ocr_elements:
            articles.append(elem.text)
    
  • 验证链接列表完整性:先打印len(article_links)确认是否收集到所有目标链接,排除链接收集阶段的问题。

2. 使用BeautifulSoup解析页面源码

完全可以,这种方式比纯Selenium操作更高效,步骤如下:
在打开文章页面并等待OCR面板加载完成后,获取页面源码再用BeautifulSoup解析:

from bs4 import BeautifulSoup
from selenium.webdriver.common.by import By
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC

article_links = []
for link in driver.find_elements_by_xpath('/html/body/div[1]/main/section[1]/ul[2]/li[*]/div[2]/div[1]/h3/a'):
    links = link.get_attribute("href")
    article_links.append(links)

articles = []
for article in article_links:
    driver.get(article)
    # 等待并点击显示OCR面板
    WebDriverWait(driver, 10).until(
        EC.element_to_be_clickable((By.CSS_SELECTOR, "#js-doc-explorer-show-additional-views"))
    ).click()
    # 等待OCR内容渲染完成
    WebDriverWait(driver, 10).until(
        EC.presence_of_element_located((By.CSS_SELECTOR, "#ocr-container > div.fulltext-ocr.js-page-ocr"))
    )
    # 获取页面源码
    page_source = driver.page_source
    # 用BeautifulSoup解析
    soup = BeautifulSoup(page_source, 'html.parser')
    ocr_divs = soup.select("#ocr-container > div.fulltext-ocr.js-page-ocr")
    for div in ocr_divs:
        articles.append(div.get_text(strip=True))

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.21 20:24:22