Selenium动态爬虫 - 爬取JavaScript渲染的页面
很多现代网站使用JavaScript动态渲染内容,传统的requests库无法获取这些数据。Selenium通过模拟真实浏览器,可以完美解决JavaScript渲染页面的爬取问题。
一、Selenium介绍
Selenium是自动化Web浏览器的工具,可以执行点击、输入、表单提交等操作。它启动一个真实的浏览器(如Chrome、Firefox),加载完整的页面内容,包括JavaScript渲染的部分。
适用场景:
- 需要登录才能访问的页面
- 使用JavaScript动态加载内容的页面
- 需要模拟复杂用户交互的场景
- 自动化测试Web应用
二、安装Selenium
pip install selenium # Chrome用户需要下载ChromeDriver # 访问 https://sites.google.com/chromedriver/ # 下载对应版本的ChromeDriver
三、基本用法
from selenium import webdriver
# 启动Chrome浏览器
driver = webdriver.Chrome()
# 访问网页
driver.get('https://www.example.com')
# 获取页面标题
print(driver.title)
# 获取页面源码
print(driver.page_source[:500])
# 获取当前URL
print(driver.current_url)
# 关闭浏览器
driver.quit()
四、元素定位
Selenium提供了多种元素定位方式:
from selenium.webdriver.common.by import By # 各种定位方式 driver.find_element(By.ID, "content") # ID定位 driver.find_element(By.NAME, "username") # NAME定位 driver.find_element(By.CLASS_NAME, "container") # CLASS_NAME定位 driver.find_element(By.TAG_NAME, "div") # 标签名定位 driver.find_element(By.XPATH, "//div[@class='container']") # XPath定位 driver.find_element(By.CSS_SELECTOR, "div.container") # CSS选择器定位 driver.find_element(By.LINK_TEXT, "点击这里") # 链接文本定位 driver.find_element(By.PARTIAL_LINK_TEXT, "点击") # 部分链接文本 # 查找所有匹配的元素(返回列表) links = driver.find_elements(By.TAG_NAME, "a")
五、等待机制
动态页面需要等待元素加载完成:
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC
# 显式等待 - 等待某个条件成立
wait = WebDriverWait(driver, 10) # 最长等待10秒
# 等待元素出现
element = wait.until(
EC.presence_of_element_located((By.ID, "content"))
)
# 常用等待条件
EC.title_is("首页") # 标题等于
EC.title_contains("首页") # 标题包含
EC.presence_of_element_located((By.ID, "id")) # 元素出现
EC.visibility_of_element_located((By.ID, "id")) # 元素可见
EC.element_to_be_clickable((By.ID, "id")) # 元素可点击
# 隐式等待(全局设置)
driver.implicitly_wait(10) # 查找元素最多等10秒
六、模拟操作
from selenium.webdriver.support.select import Select
# 点击元素
driver.find_element(By.ID, "submit").click()
# 输入文本
search_box = driver.find_element(By.NAME, "q")
search_box.send_keys("Python爬虫") # 输入文本
# 清除输入
search_box.clear()
# 下拉选择
select = Select(driver.find_element(By.NAME, "dropdown"))
select.select_by_visible_text("选项1") # 按显示文本选择
select.select_by_value("option1") # 按value选择
select.select_by_index(0) # 按索引选择
# 拖拽元素
from selenium.webdriver import ActionChains
draggable = driver.find_element(By.ID, "draggable")
droppable = driver.find_element(By.ID, "droppable")
ActionChains(driver).drag_and_drop(draggable, droppable).perform()
# 执行JavaScript
driver.execute_script("window.scrollTo(0, document.body.scrollHeight)") # 滚动到底部
driver.execute_script("alert('Hello')") # 执行JS代码
七、获取数据
element = driver.find_element(By.ID, "content")
# 获取文本
print(element.text) # 元素内所有文本
# 获取属性
print(element.get_attribute('href')) # 获取href属性
print(element.get_attribute('class')) # 获取class属性
print(element.get_attribute('innerHTML')) # 获取HTML
# 获取CSS样式
print(element.value_of_css_property('color'))
print(element.value_of_css_property('font-size'))
八、Cookie和窗口管理
# 获取Cookie
cookies = driver.get_cookies()
print(cookies)
# 添加Cookie
driver.add_cookie({'name': 'session', 'value': 'abc123'})
# 删除Cookie
driver.delete_cookie('session')
driver.delete_all_cookies()
# 切换窗口/标签页
driver.switch_to.window(driver.window_handles[1]) # 切换到第二个标签页
driver.close() # 关闭当前标签页
driver.switch_to.window(driver.window_handles[0]) # 切换回第一个
# 切换frame
driver.switch_to.frame("frame_name_or_id")
driver.switch_to.default_content() # 切换回主文档
九、实践案例
模拟登录并爬取数据:
from selenium import webdriver
from selenium.webdriver.common.by import By
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import EC
def login_and_scrape():
driver = webdriver.Chrome()
driver.get('https://www.example.com/login')
# 显式等待登录框出现
wait = WebDriverWait(driver, 10)
username = wait.until(
EC.presence_of_element_located((By.NAME, "username"))
)
# 输入账号密码
username.send_keys('your_username')
driver.find_element(By.NAME, 'password').send_keys('your_password')
# 点击登录按钮
driver.find_element(By.XPATH, "//button[@type='submit']").click()
# 等待登录成功后的页面
wait.until(EC.url_contains('/dashboard'))
# 爬取数据
data = driver.find_elements(By.CLASS_NAME, 'data-item')
for item in data:
print(item.text)
driver.quit()
login_and_scrape()
十、常见问题和技巧
- ChromeDriver版本不匹配 - 下载与Chrome版本对应的ChromeDriver
- 提高稳定性 - 总是使用显式等待而非隐式等待
- 处理弹窗 - 使用driver.switch_to.alert()处理alert
- 无头模式 - headless=True不显示浏览器窗口
- 反检测 - 禁用自动化标记webdriver
十一、总结
Selenium是爬取JavaScript渲染页面的利器,但相比requests速度较慢。建议:需要登录或渲染页面时使用Selenium,普通页面用requests+BeautifulSoup组合。
声明:本站所有文章,如无特殊说明或标注,均为本站原创发布。任何个人或组织,在未征得本站同意时,禁止复制、盗用、采集、发布本站内容到任何网站、书籍等各类媒体平台。如若本站内容侵犯了原著者的合法权益,可联系我们进行处理。







