首页 > 解决方案 > 带有 Selenium 刮板的 Python 跳过了一些内容

问题描述

我正在尝试从网站https://rsoe-edis.org/eventList抓取数据并保存到 xlsx 文件。刮板没有显示任何错误,但它跳过了一些内容。它保存所有链接,但在某些情况下它不显示其他信息。为什么?

import xlsxwriter
from datetime import datetime

now = (datetime.now()).strftime("%d-%m-%Y_%H-%M")

PATH = "C:\Program Files (x86)\chromedriver.exe"
driver = webdriver.Chrome(PATH)

workbook = xlsxwriter.Workbook("RSOE_" + now + ".xlsx")

worksheet = workbook.add_worksheet("EventList") 

#Open the website
driver.get("https://rsoe-edis.org/eventList")

#Take events list
articles = driver.find_elements_by_tag_name("tr")
row = 0
col = 0

for article in articles:
        
        header = article.find_element_by_class_name("title")
        date = article.find_element_by_class_name("eventDate")
        location = article.find_element_by_class_name("location")
        link = article.find_element_by_tag_name("a")  
        worksheet.write(row, col,     header.text)
        worksheet.write(row, col + 1, date.text)
        worksheet.write(row, col + 2, location.text)
        worksheet.write(row, col + 3, link.get_attribute("href"))   

        print(header.text)

        row += 1      
workbook.close()      

driver.close()```

标签: pythonseleniumweb-scraping

解决方案


问题说明

您的问题是隐藏的事件卡很多(具有样式属性display:none;),Selenium 无法通过 webelements.text属性提供隐藏元素的文本内容。

解决方案

要与隐藏的元素进行交互,您可以:

  • 取而代之的是获取 webelements 属性值(例如.get_attribute("innerText")
  • 使用原始 JavaScript 取消隐藏元素,然后继续.text.
  • 使用原始 JavaScript 获取所有 web 元素

使用获取元素文本内容的示例.get_attribute()

这里我使用.get_attribute()webelement 的方法通过innerText属性获取内容,然后使用字符串.strip()方法删除前导和尾随空格

driver.get("https://rsoe-edis.org/eventList")
articles = driver.find_elements_by_tag_name("tr")
with open("my_articles.csv", "wt") as f:
    for article in articles:
        header = article.find_element_by_class_name("title").get_attribute("innerText").strip()
        date = article.find_element_by_class_name("eventDate").get_attribute("innerText").strip()
        location = article.find_element_by_class_name("location").get_attribute("innerText").strip()
        link = article.find_element_by_tag_name("a").get_attribute("href")
        f.write(f"{header}, {date}, {location}, {link}\n")

启用原始 JavaScript 的示例取消隐藏元素.text

下面是一个示例,我使用第二种方法style="display:none;"从所有隐藏卡片中删除属性,然后继续使用 webelements .text 属性来获取文本内容。从这个例子中你需要的是注释下面的 3 行 # Loop through event list and unhide all event card

#Open the website
driver.get("https://rsoe-edis.org/eventList")

# Loop through event list and unhide all event cards
event_cards = driver.find_elements_by_class_name("event-card")
for card in event_cards:
    driver.execute_script("arguments[0].removeAttribute(\"style\")", card)

# Find all articles and add them to a file
articles = driver.find_elements_by_tag_name("tr")
with open("my_articles.csv", "wt") as f:
    for article in articles:
        header = article.find_element_by_class_name("title").text
        date = article.find_element_by_class_name("eventDate").text
        location = article.find_element_by_class_name("location").text
        link = article.find_element_by_tag_name("a").get_attribute("href")
        f.write(f"{header}, {date}, {location}, {link}\n")

推荐阅读