--------------------------------------------------------------------------- NoSuchElementException Traceback (most recent call last) ~\anaconda3\lib\site-packages\selenium\webdriver\remote\switch_to.py in frame(self, frame_reference) 87 try: ---> 88 frame_reference = self._driver.find_element(By.ID, frame_reference) 89 except NoSuchElementException: ~\anaconda3\lib\site-packages\selenium\webdriver\remote\webdriver.py in find_element(self, by, value) 897 --> 898 return self.execute(Command.FIND_ELEMENT, {"using": by, "value": value})["value"] 899 ~\anaconda3\lib\site-packages\selenium\webdriver\remote\webdriver.py in execute(self, driver_command, params) 428 if response: --> 429 self.error_handler.check_response(response) 430 response["value"] = self._unwrap_value(response.get("value", None)) ~\anaconda3\lib\site-packages\selenium\webdriver\remote\errorhandle
时间: 2025-05-26 14:55:29 浏览: 27
### 解决 `NoSuchElementException` 并成功爬取QQ邮箱收件箱信息
在使用 Selenium 进行网页自动化时,如果定位不到某个元素会抛出 `NoSuchElementException` 错误。这通常是由于以下几个原因造成的:页面未完全加载、元素被 iframe 嵌套、CSS Selector 或 XPath 表达式不匹配等[^1]。
为了避免该错误的发生,可以采取以下措施:
#### 方法一:显式等待
通过设置显式等待条件来确保目标元素已经加载完成再执行后续操作。
```python
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC
try:
element = WebDriverWait(driver, 10).until(
EC.presence_of_element_located((By.ID, "element_id"))
)
finally:
driver.quit()
```
#### 方法二:捕获异常并重试
利用 try-except 结构捕捉可能出现的 `NoSuchElementException` ,并在发生异常时重新尝试查找元素。
```python
for attempt in range(retries):
try:
el = driver.find_element(By.ID, ID)
break
except NoSuchElementException:
if attempt < retries - 1:
time.sleep(wait_time_between_attempts)
else:
raise
```
#### 完整版改进后的代码示例
基于之前的实现逻辑,这里提供了一个更加健壮的版本,能够有效应对各种潜在问题,包括但不限于 `NoSuchElementException` 的处理[^2]:
```python
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.common.exceptions import TimeoutException, NoSuchElementException
import time
import csv
def fetch_qq_email_data(username, password, max_retries=3, wait_time=5):
options = webdriver.ChromeOptions()
options.add_argument('--headless') # 可选参数
driver = webdriver.Chrome(options=options)
def safe_find_element(by, value, retry_count=max_retries):
attempts = 0
while attempts < retry_count:
try:
return driver.find_element(by, value)
except (TimeoutException, NoSuchElementException):
time.sleep(wait_time)
attempts += 1
raise Exception("Element not found after multiple attempts.")
try:
# 登录流程保持不变...
driver.get('https://mail.qq.com/')
login_frame = WebDriverWait(driver, 10).until(EC.frame_to_be_available_and_switch_to_it(('login_frame')))
switch_login_mode = safe_find_element(By.ID, 'switcher_plogin')
switch_login_mode.click()
username_field = safe_find_element(By.ID, 'u')
password_field = safe_find_element(By.ID, 'p')
username_field.clear()
username_field.send_keys(username)
password_field.clear()
password_field.send_keys(password)
submit_btn = safe_find_element(By.ID, 'login_button')
submit_btn.click()
main_frame = WebDriverWait(driver, 10).until(EC.frame_to_be_available_and_switch_to_it(('mainFrame')))
email_list = []
for _ in range(max_retries): # 循环读取直到找到数据为止
try:
rows = driver.find_elements(By.CSS_SELECTOR, '.nxm_item.nxm_normal')
for row in rows:
sender_name_el = row.find_elements(By.CSS_SELECTOR, "td .tf span")
if sender_name_el:
sender_name = sender_name_el[0].text.strip()
sender_email = sender_name_el[0].get_attribute("title").strip() or ""
title_el = row.find_element(By.CSS_SELECTOR, ".gt a")
mail_title = title_el.text.strip()
date_received_el = row.find_element(By.CSS_SELECTOR, ".ft td:nth-child(6)")
receive_date = date_received_el.text.strip()
email_list.append([sender_name, sender_email, mail_title, receive_date])
break
except (TimeoutException, NoSuchElementException):
time.sleep(wait_time)
finally:
driver.quit()
return email_list
def store_emails_as_csv(emails, filepath="output.csv"):
with open(filepath, mode='w', newline='', encoding='utf-8') as f:
writer = csv.writer(f)
writer.writerow(["发件人", "发件人邮箱", "邮件标题", "收信日期"])
writer.writerows(emails)
if __name__ == '__main__':
qq_user = input("请输入您的QQ账号:")
qq_pwd = input("请输入您的QQ密码:")
emails_fetched = fetch_qq_email_data(qq_user, qq_pwd)
store_emails_as_csv(emails_fetched)
```
---
###
阅读全文