如何用BeautifulSoup或Selenium爬取YouTube频道所有视频时长
核心问题原因
- 你用requests+BeautifulSoup拿不到对应元素是正常现象:YouTube的视频列表属于前端动态渲染内容,服务端返回的初始HTML仅包含页面框架,所有视频数据都是页面加载完成后通过JS异步请求接口再渲染到页面上的,requests只能拿到未渲染的初始HTML,自然找不到你在审查元素里看到的div节点。
- Selenium定位报错的原因是你触发页面跳转后立刻查找元素,此时页面还未完成渲染,目标元素还没有生成,所以会报找不到元素的错误。另外YouTube的视频是懒加载机制,不滚动页面的话最多只会加载第一屏的20~30条视频,拿不到全量数据。
方案1:Selenium实现步骤
直接修改你原来的代码即可,改动点如下:
- 增加页面加载等待机制
- 增加自动滚动逻辑加载全量视频
- 批量定位元素提取时长
示例代码:
from selenium import webdriver from selenium.webdriver.common.by import By import time # 你本地的chromedriver路径 PATH = r"你的chromedriver.exe路径" driver = webdriver.Chrome(PATH) # 隐式等待10秒,所有查找元素的操作最多等10秒,没找到才报错 driver.implicitly_wait(10) driver.get(r"https://www.youtube.com/c/0214mex/videos?view=0&sort=dd&shelf_id=0") # 滚动页面加载全部视频,你可以根据频道视频总数调整滚动间隔和终止条件 last_height = driver.execute_script("return document.documentElement.scrollHeight") while True: driver.execute_script("window.scrollTo(0, document.documentElement.scrollHeight);") time.sleep(2) new_height = driver.execute_script("return document.documentElement.scrollHeight") if new_height == last_height: break last_height = new_height # 批量获取所有视频时长 duration_list = [] duration_elements = driver.find_elements(By.CSS_SELECTOR, "ytd-thumbnail-overlay-time-status-renderer") for ele in duration_elements: duration = ele.text.strip() if duration: # 过滤掉空的无效元素 duration_list.append(duration) print(duration_list) driver.quit()
方案2:无需Selenium的更简单实现
不需要自己处理动态渲染和元素定位,直接用第三方库yt-dlp实现,几行代码就能拿到所有视频数据:
- 先执行安装命令:
pip install yt-dlp - 运行如下代码:
import yt_dlp channel_url = "https://www.youtube.com/c/0214mex/videos" ydl_opts = { 'extract_flat': 'in_playlist', # 只提取列表信息,不下载视频 'skip_download': True, } duration_list = [] with yt_dlp.YoutubeDL(ydl_opts) as ydl: info = ydl.extract_info(channel_url, download=False) for entry in info['entries']: # 可直接取格式化好的时长字符串,也可以取duration字段拿到秒级数值自己转换格式 duration_list.append(entry.get('duration_string')) print(duration_list)
这个方案不需要处理浏览器驱动、页面加载、元素定位等问题,稳定性比自己写Selenium爬虫高很多。
内容的提问来源于stack exchange,提问作者yami123
相关产品推荐
相关产品推荐

