使用Python+wxPython+Selenium打造智能网页截图工具

Python智能网页截图工具
部署运行你感兴趣的模型镜像

前言

在网站测试、UI审查或文档编写过程中,我们常常需要对网站的所有页面进行截图记录。手动逐页访问并截图不仅效率低下,还容易遗漏。今天,我将分享如何使用Python开发一个自动化工具,实现一键遍历网站所有链接并生成带截图的Excel报告。
C:\pythoncode\new\web_link_clicker.py

项目需求

我们的目标是开发一个桌面应用程序,具备以下功能:

  1. 自动提取站内链接:解析网页中的所有同域名链接
  2. 智能点击操作:首次访问时自动点击特定按钮(如"进入关怀版")
  3. 完整页面截图:截取包括滚动区域在内的整个网页
  4. 生成详细报告:将链接信息和截图整理成Excel表格

技术选型

核心技术栈

  • wxPython:构建图形用户界面
  • Selenium:控制浏览器自动化操作
  • BeautifulSoup:解析HTML提取链接
  • OpenPyXL:生成Excel报告

为什么选择Selenium?

相比传统的网页截图方案,Selenium具有以下优势:

  • ✅ 支持完整页面截图(包括滚动区域)
  • ✅ 可以执行JavaScript交互操作
  • ✅ 支持多种浏览器(Chrome、Firefox等)
  • ✅ 能够处理动态加载的内容

核心功能实现

1. GUI界面设计

使用wxPython创建简洁直观的操作界面:

class WebLinkClickerFrame(wx.Frame):
    def __init__(self):
        super().__init__(parent=None, title='网页链接自动点击截图工具', size=(900, 700))
        
        # URL输入框
        self.url_input = wx.TextCtrl(panel, value="https://example.com")
        
        # 浏览器选择
        self.browser_choice = wx.Choice(panel, choices=['Chrome', 'Firefox'])
        
        # 功能选项
        self.headless_cb = wx.CheckBox(panel, label="无头模式(后台运行)")
        self.full_page_cb = wx.CheckBox(panel, label="完整页面截图")
        self.delay_spin = wx.SpinCtrl(panel, value="2", min=1, max=10)
        
        # 进度显示
        self.progress_text = wx.TextCtrl(panel, style=wx.TE_MULTILINE | wx.TE_READONLY)
        self.progress_gauge = wx.Gauge(panel, range=100)

界面包含以下要素:

  • URL输入框和浏览器选择
  • 无头模式、完整截图等选项
  • 实时日志显示和进度条
  • 开始/停止按钮

2. Selenium浏览器初始化

支持Chrome和Firefox两种浏览器,并提供无头模式选项:

def init_driver(self):
    browser_type = self.browser_choice.GetStringSelection()
    headless = self.headless_cb.GetValue()
    
    if browser_type == 'Chrome':
        options = Options()
        if headless:
            options.add_argument('--headless')
        options.add_argument('--no-sandbox')
        options.add_argument('--window-size=1920,1080')
        
        self.driver = webdriver.Chrome(options=options)
    else:
        options = FirefoxOptions()
        if headless:
            options.add_argument('--headless')
        
        self.driver = webdriver.Firefox(options=options)

关键配置说明

  • --headless:后台运行,不显示浏览器窗口
  • --no-sandbox:避免权限问题
  • --window-size:设置浏览器窗口大小

3. 智能按钮点击

实现首次访问时自动点击"进入关怀版"按钮,使用多种定位策略提高成功率:

def click_care_button(self):
    care_button = None
    
    # 方式1: 通过文本内容查找
    try:
        care_button = self.driver.find_element(By.XPATH, "//*[contains(text(), '进入关怀版')]")
    except:
        pass
    
    # 方式2: 通过链接文本查找
    if not care_button:
        try:
            care_button = self.driver.find_element(By.LINK_TEXT, "进入关怀版")
        except:
            pass
    
    # 方式3: 通过部分链接文本查找
    if not care_button:
        try:
            care_button = self.driver.find_element(By.PARTIAL_LINK_TEXT, "关怀版")
        except:
            pass
    
    # 方式4: 遍历所有按钮
    if not care_button:
        buttons = self.driver.find_elements(By.TAG_NAME, "button")
        for btn in buttons:
            if "关怀版" in btn.text:
                care_button = btn
                break
    
    # 点击按钮
    if care_button:
        care_button.click()
        time.sleep(2)  # 等待页面跳转

定位策略

  1. XPath文本内容匹配
  2. 完整链接文本
  3. 部分链接文本
  4. 遍历button标签
  5. 遍历a标签

这种多重策略能够应对不同网站的HTML结构差异。

4. 站内链接提取

使用BeautifulSoup解析HTML,筛选出所有站内链接:

def extract_links(self, url):
    self.driver.get(url)
    time.sleep(self.delay_spin.GetValue())
    
    # 点击特定按钮(如果存在)
    self.click_care_button()
    
    # 解析页面
    html = self.driver.page_source
    soup = BeautifulSoup(html, 'html.parser')
    base_domain = urlparse(url).netloc
    
    # 提取链接
    links = []
    for a_tag in soup.find_all('a', href=True):
        href = a_tag['href']
        full_url = urljoin(url, href)
        
        # 只保留站内链接
        if urlparse(full_url).netloc == base_domain:
            link_text = a_tag.get_text(strip=True) or '无标题'
            links.append({'text': link_text, 'url': full_url})
    
    # 去重
    unique_links = []
    seen_urls = set()
    for link in links:
        if link['url'] not in seen_urls:
            seen_urls.add(link['url'])
            unique_links.append(link)
    
    return unique_links

关键点

  • 使用urljoin处理相对路径
  • 通过域名比对筛选站内链接
  • 自动去重避免重复截图

5. 完整页面截图

这是整个项目的核心功能。使用Chrome的CDP(Chrome DevTools Protocol)实现真正的全页面截图:

def take_full_page_screenshot(self, filepath):
    if isinstance(self.driver, webdriver.Chrome):
        # 获取页面完整尺寸
        metrics = self.driver.execute_cdp_cmd('Page.getLayoutMetrics', {})
        width = metrics['contentSize']['width']
        height = metrics['contentSize']['height']
        
        # 使用CDP截图
        screenshot = self.driver.execute_cdp_cmd('Page.captureScreenshot', {
            'clip': {
                'width': width,
                'height': height,
                'x': 0,
                'y': 0,
                'scale': 1
            },
            'captureBeyondViewport': True  # 关键参数
        })
        
        # 保存截图
        import base64
        with open(filepath, 'wb') as f:
            f.write(base64.b64decode(screenshot['data']))
    else:
        # Firefox使用标准方法
        self.driver.save_screenshot(filepath)

技术亮点

  • Page.getLayoutMetrics:获取页面真实尺寸
  • captureBeyondViewport: True:允许截取视口外内容
  • 自动处理base64编码

6. 生成Excel报告

使用OpenPyXL将数据和截图整合到Excel文件:

def generate_excel(self):
    wb = openpyxl.Workbook()
    ws = wb.active
    ws.title = "链接截图报告"
    
    # 设置表头
    headers = ['序号', '按钮名称', '链接地址', '截图']
    ws.append(headers)
    
    # 设置列宽
    ws.column_dimensions['B'].width = 30
    ws.column_dimensions['C'].width = 50
    ws.column_dimensions['D'].width = 60
    
    # 添加数据和截图
    for data in self.links_data:
        row = ws.max_row + 1
        ws.cell(row, 1, data['index'])
        ws.cell(row, 2, data['text'])
        ws.cell(row, 3, data['url'])
        
        # 插入截图
        if data['screenshot'] and os.path.exists(data['screenshot']):
            img = XLImage(data['screenshot'])
            img.width = 400
            img.height = 300
            ws.add_image(img, f'D{row}')
            ws.row_dimensions[row].height = 225
    
    # 保存文件
    excel_path = os.path.join(self.screenshot_dir, "链接报告.xlsx")
    wb.save(excel_path)

报表特点

  • 自动调整列宽和行高
  • 嵌入式截图,直接查看
  • 包含序号、标题、URL等完整信息

7. 多线程处理

为避免阻塞UI,将耗时操作放在独立线程中执行:

def on_start(self, event):
    self.is_running = True
    thread = threading.Thread(target=self.run_analysis, args=(url,))
    thread.daemon = True
    thread.start()

def run_analysis(self, url):
    try:
        # 初始化浏览器
        self.init_driver()
        
        # 提取链接
        links = self.extract_links(url)
        
        # 处理每个链接
        for index, link in enumerate(links):
            if not self.is_running:  # 支持中途停止
                break
            
            self.process_link(link, index)
            self.update_progress(int((index / len(links)) * 100))
        
        # 生成报告
        self.generate_excel()
    finally:
        self.driver.quit()

线程安全

  • 使用wx.CallAfter更新UI
  • 设置daemon=True确保程序能够正常退出
  • 添加停止标志支持用户中断

安装部署

1. 安装Python依赖

pip install wxPython selenium beautifulsoup4 openpyxl pillow

2. 安装浏览器驱动

Chrome驱动(推荐)

# 自动管理驱动
pip install webdriver-manager

或手动下载:ChromeDriver下载

Firefox驱动
GeckoDriver Releases 下载

3. 运行程序

python web_link_clicker.py

使用指南

基本操作

  1. 输入URL:在输入框中填写要分析的网站首页地址
  2. 选择浏览器:Chrome或Firefox(推荐Chrome)
  3. 配置选项
    • 勾选"无头模式"后台运行
    • 勾选"完整页面截图"捕获整个页面
    • 调整页面加载延迟(1-10秒)
  4. 开始分析:点击"开始分析"按钮
  5. 查看结果:完成后会弹出提示,在生成的文件夹中查看Excel报告

运行流程

输入URL → 点击开始 → 初始化浏览器 → 打开首页 
    ↓
点击"进入关怀版"(如有)→ 提取所有站内链接 
    ↓
逐个访问链接 → 完整页面截图 → 更新进度 
    ↓
生成Excel报告 → 关闭浏览器 → 完成

输出内容

程序会在工作目录下生成一个以时间戳命名的文件夹,包含:

  • 所有截图PNG文件:按序号_链接名称命名
  • 链接报告.xlsx:包含序号、按钮名称、URL和嵌入截图的完整报告

功能特色

1. 智能容错

  • 找不到特定按钮时自动跳过,不影响后续流程
  • 截图失败时记录日志但继续处理其他链接
  • 支持中途停止,已完成的数据会被保留

2. 用户体验

  • 实时日志显示当前操作
  • 进度条展示任务完成度
  • 完成后自动弹出文件路径提示

3. 灵活配置

  • 无头模式节省系统资源
  • 可调节延迟适应不同网速
  • 支持Chrome和Firefox双浏览器

实际应用场景

1. 网站测试

QA团队可以使用此工具快速生成网站所有页面的截图档案,便于:

  • 版本对比
  • UI一致性检查
  • 问题定位和记录

2. 文档编写

技术文档编写者可以:

  • 自动生成产品界面截图
  • 制作操作手册配图
  • 更新帮助文档

3. 竞品分析

市场人员可以:

  • 快速获取竞品网站截图
  • 分析页面布局和功能
  • 制作对比报告

4. 网站归档

运维团队可以:

  • 定期保存网站状态
  • 版本发布前后对比
  • 历史版本存档

进阶优化

1. 添加webdriver-manager

自动管理浏览器驱动版本:

from webdriver_manager.chrome import ChromeDriverManager
from selenium.webdriver.chrome.service import Service

service = Service(ChromeDriverManager().install())
self.driver = webdriver.Chrome(service=service, options=options)

2. 增加等待策略

使用显式等待提高稳定性:

from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC

wait = WebDriverWait(self.driver, 10)
element = wait.until(EC.presence_of_element_located((By.ID, "content")))

3. 添加异常处理

更细致的错误分类:

try:
    self.driver.get(url)
except TimeoutException:
    self.log("页面加载超时")
except WebDriverException as e:
    self.log(f"浏览器错误: {str(e)}")

4. 支持更多格式

除了Excel,还可以生成:

  • PDF报告
  • HTML网页
  • Markdown文档

常见问题

Q1: Chrome驱动版本不匹配

解决方案

  • 使用webdriver-manager自动管理
  • 或手动下载与Chrome版本匹配的驱动

Q2: 截图不完整

确保勾选"完整页面截图",且使用Chrome浏览器(Firefox不支持完整截图)

Q3: 页面加载太慢

增加"页面加载延迟"时间,或检查网络连接

Q4: 找不到"进入关怀版"按钮

这是正常的,程序会自动跳过此步骤继续执行

运行结果

在这里插入图片描述

您可能感兴趣的与本文相关的镜像

Python3.10

Python3.10

Conda
Python

Python 是一种高级、解释型、通用的编程语言,以其简洁易读的语法而闻名,适用于广泛的应用,包括Web开发、数据分析、人工智能和自动化脚本

评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值