05 selenium网页截长图(无头浏览器)

983 阅读3分钟

持续创作,加速成长!这是我参与「掘金日新计划 · 10 月更文挑战」的第5天,点击查看活动详情

「selenium实战专栏」将记录selenium实战(Python版)过程,以及各类问题的解决方案。

大致规划如下:

  • 利用Element UI组件库联系对各种元素的操作
  • 利用一个真实网站进行部分页面UI自动化实战

使用版本如下:

  • Python 3.10.6
  • selenium 4.0.5

上节以ElementUI网页为例,演示了如何进行网页滚动截图,其主要思路如下:

  • 获取到所有的元素,执行JS语句将元素标红
  • 滑动屏幕,循环截取当前窗口的图片
  • 通过PIL将图片进行拼接

本节提供另外一种方案,使用无头浏览器,主要思路如下:

  • 获取到所有的元素,执行JS语句将元素标红
  • 获取网页最大高度,将浏览器尺寸设置为最大高度
  • 对整个网页进行截图

第一个步骤同样不做介绍,想了解的可以查看专栏文章,本节主要处理后面两步。

首先给Chrome浏览器增加启动参数headless用于启动一个无头浏览器,即没有可视化界面的浏览器。

service = Service(executable_path='/Users/huyanping/Softwares/chromedriver')

options = ChromeOptions()
options.add_argument('headless')
driver = webdriver.Chrome(service=service, options=options)

完成元素标红动作后,设置无头浏览器的尺寸,宽度可根据网页的具体内容进行设置,高度要设置为最大滑动高度,上节已经介绍了获取网页滑动高度的js语句document.body.scrollHeight

# 获取网页高度
body_height = driver.execute_script('return document.body.scrollHeight;')
# 设置窗口尺寸 宽度可根据截取网页的宽度进行调整
driver.set_window_size(width="1920", height=body_height)

driver.save_screenshot("截图.png")

执行脚本可以看到,完整的网页被截图了,完整图片比较大,这里只粘贴部分,感兴趣的伙伴可自行进行尝试。

无头浏览器没有电脑窗口大小的限制了,可以设置为任意满足要求的长度和宽度,将内容全部展示完成后,再操作进行网页截图,这样就完成了网页截长图的功能,想较于上一节滚动窗口截图+拼接的方式更推荐使用无头浏览器,更加方便快捷。

完整代码如下:

from selenium import webdriver
from selenium.webdriver.chrome.options import Options as ChromeOptions
from selenium.webdriver.chrome.service import Service
from selenium.webdriver.common.by import By

service = Service(executable_path='/Users/huyanping/Softwares/chromedriver')

options = ChromeOptions()
options.add_argument('headless')
driver = webdriver.Chrome(service=service, options=options)

driver.get("https://element-plus.gitee.io/zh-CN/component/link.html")

# 隐式等待,暂时可以先不用管
driver.implicitly_wait(10)
# element-ui页面会请求一些外部页面,导致需要很长时间的等待,
# 可以设置超时时间避免需要等待很长时间,但是可能会导致元素还没加载出来,可以根据自己的网络对超时时间进行调整
driver.set_page_load_timeout(6)

# 通过JS语句设置元素属性style arguments是参数
js = "arguments[0].setAttribute('style', arguments[1]);"
# css语句,给元素添加边框
style = "border: 5px solid red;"
elements = driver.find_elements(By.PARTIAL_LINK_TEXT, 'i')
for index in range(len(elements)):
    # 执行JS语句,将元素作为参数传递
    driver.execute_script(js, elements[index], style)

# 获取网页高度
body_height = driver.execute_script('return document.body.scrollHeight;')
# 设置窗口尺寸 宽度可根据截取网页的宽度进行调整
driver.set_window_size(width="1920", height=body_height)

driver.save_screenshot("截图.png")

# 因为点击操作执行完成后,很快就会关闭浏览器无法看到效果,调试的时候可以先注释掉
# 但是要记得自己手动关闭浏览器,避免开很多的浏览器未关闭消耗电脑内存
# driver.quit()