如何用Selenium抓取网页ApexCharts嵌入的通勤时间序列数据
抓取纽约市拥堵区域通勤时间对比图表数据的解决方案
核心思路
ApexCharts的时间序列数据点仅在鼠标悬停时才会显示完整tooltip信息,因此需要通过Selenium定位图表中的每个数据点元素,逐个触发悬停操作,提取tooltip中的日期和两组通勤时间数据,最终整理成结构化字典。
完整实现代码
from selenium import webdriver from selenium.webdriver.common.by import By from selenium.webdriver.support.ui import WebDriverWait from selenium.webdriver.support import expected_conditions as EC from selenium.webdriver.common.action_chains import ActionChains import time # 初始化WebDriver driver = webdriver.Chrome() driver.get("https://www.congestion-pricing-tracker.com/") try: # 等待页面加载完成,定位到最后一张图表的y轴标题 WebDriverWait(driver, 15).until( EC.presence_of_all_elements_located((By.CLASS_NAME, "apexcharts-yaxis-title")) ) y_axis_titles = driver.find_elements(By.CLASS_NAME, "apexcharts-yaxis-title") last_chart_title = y_axis_titles[-1] # 滚动到最后一张图表位置 driver.execute_script("arguments[0].scrollIntoView({block: 'center'});", last_chart_title) time.sleep(3) # 等待图表完全渲染 # 定位最后一张图表的所有数据点标记 last_chart = last_chart_title.find_element(By.XPATH, "./ancestor::div[contains(@class, 'apexcharts-chart')]") data_points = last_chart.find_elements(By.CLASS_NAME, "apexcharts-series-markers") # 存储最终数据的列表 commute_data = [] actions = ActionChains(driver) for point in data_points: try: # 悬停数据点触发tooltip actions.move_to_element(point).perform() time.sleep(0.5) # 等待tooltip加载 # 提取日期 date_element = WebDriverWait(driver, 5).until( EC.presence_of_element_located((By.CLASS_NAME, "apexcharts-xaxistooltip-text")) ) date = date_element.text.strip() # 提取两个系列的通勤时间 y_labels = driver.find_elements(By.CLASS_NAME, "apexcharts-tooltip-text-y-label") y_values = driver.find_elements(By.CLASS_NAME, "apexcharts-tooltip-text-y-value") # 构建单条数据字典 single_data = {"date": date} for label, value in zip(y_labels, y_values): label_text = label.text.strip().replace(":", "") value_text = value.text.strip() single_data[label_text] = value_text commute_data.append(single_data) except Exception as e: print(f"处理数据点时出错: {e}") continue # 打印结果 print("抓取到的通勤时间数据:") for item in commute_data: print(item) finally: # 关闭浏览器 driver.quit()
关键步骤说明
- 精准定位目标图表:通过最后一个
apexcharts-yaxis-title元素向上查找父容器,锁定目标图表,避免误操作其他图表元素。 - 遍历触发悬停:每个数据点对应
apexcharts-series-markers类元素,遍历这些元素逐个触发悬停,唤起tooltip。 - 提取结构化数据:悬停后等待tooltip加载,分别提取日期、系列标签和对应数值,整理成键值对形式。
- 容错处理:添加try-except块处理单个数据点的加载失败问题,保证整体抓取流程不中断。
内容的提问来源于stack exchange,提问作者Jared Greathouse
相关产品推荐
相关产品推荐

