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

Python/Selenium:类实例化或定位器问题致元素查找失败?

问题根源与修复方案

核心错误:WebDriverWait 参数传递错误

你在BookingFilters类的wait_for_clickable方法里犯了关键错误:WebDriverWait的第一个参数必须传入Selenium的driver实例,而非BookingFilters类自身。

在Booking类中,因为它继承了webdriver.Chrome,self本身就是driver实例,所以WebDriverWait(self, ...)调用正确;但BookingFilters类的self是类实例,不是driver,必须用self.driver传入WebDriverWait才有效。

其他次要问题

  1. 导入缺失:BookingFilters.py未导入WebDriver、WebDriverWait、EC等必要模块,运行时会报错。
  2. 定位器类型不匹配://div[text()="2 stars"]是XPATH表达式,你在Booking类的测试代码里错误使用了By.CSS_SELECTOR,需对应By.XPATH。
  3. 定位器语法错误:div[data-filters-item*="class]的引号未闭合,正确写法是div[data-filters-item*="class"]。

修复后的代码

修改后的 BookingFilters.py

from selenium.webdriver.remote.webdriver import WebDriver
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC
from selenium.webdriver.common.by import By

class BookingFilters:
    def __init__(self, driver: WebDriver):
        self.driver = driver

    def apply_star_rating(self):
        star_filter_area = self.wait_for_clickable((By.CSS_SELECTOR, 'div[data-filters-group="class"]'))
        # 修正定位器类型为XPATH
        star_filter_selection = self.wait_for_clickable((By.XPATH, '//div[text()="2 stars"]'))
        print(star_filter_selection)
        if star_filter_area is not None:
            # 修正引号闭合问题
            star_box = star_filter_area.find_elements(By.CSS_SELECTOR, 'div[data-filters-item*="class"]')
            for element in star_box:
                html = element.get_attribute('outerHTML')
                print(html)

    def wait_for_clickable(self, locator, timeout=1, poll_frequency=0.05):
        try:
            print(f'Trying to find element with {locator}')
            # 关键修复:传入self.driver而非self
            element_found = WebDriverWait(self.driver, timeout=timeout, poll_frequency=poll_frequency) \
                .until(EC.element_to_be_clickable(locator))
            element_html = element_found.get_attribute('outerHTML')
            if element_found:
                print(f'Element found: {element_html}\n')
            return element_found
        except:
            print(f'============ element with {locator} Not Found ============\n')
            return None

修正Booking.py中的定位器类型错误

在apply_filters方法的测试代码中,把:

star_filter_selection = self.wait_for_clickable((By.CSS_SELECTOR, '//div[text()="2 stars"]'))

改为:

star_filter_selection = self.wait_for_clickable((By.XPATH, '//div[text()="2 stars"]'))

关于类封装思路的合理性

你的封装思路完全没问题,把筛选逻辑抽离到单独的BookingFilters类符合单一职责原则,能让代码更清晰易维护,问题只是实现时的参数传递错误,和思路无关。

额外优化建议

  1. 抽取公共基类:将wait_for_clickable这类通用等待方法抽离到基类中,让Booking和BookingFilters继承,避免重复代码。
  2. 延长等待时长:当前1秒的timeout太短,容易因页面加载慢导致查找失败,可延长至5-10秒。
  3. 明确捕获异常:避免空except语句,建议捕获TimeoutException等Selenium特定异常,方便调试。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.02 08:10:24