我有这样一个用于在 YouTube 上搜索的脚本(我在电报机器人中使用它):
import urllib
import re
import random
link = urllib.parse.urlencode({"search_query": msg})
content = urllib.request.urlopen("https://www.youtube.com/results?" + link)
search_results = re.findall('href=\"\/watch\?v=(.*?)\"', content.read().decode())
if len(search_results) > 0:
search_results = search_results[0:9:1]
choice_f = random.choice(search_results)
yt_link = "https://www.youtube.com/watch?v="+choice_f
他不整洁,他通过正则表达式工作,总的来说,他不是我的:)
现在它没有返回任何东西,我想弄清楚发生了什么变化以及如何修复它。
简而言之(我想要更多详细信息,请参见下文),然后该脚本可以正常工作,因为搜索结果是在对请求的响应中以 HTML 格式返回的。
现在搜索结果将在javascript中,需要对其进行提取和处理。
现成的解决方案(2020 年 10 月 28 日更新,支持
var ytInitialData):现在更多
让我们从一开始就尝试处理解析。下面会有很多截图!
首先,我们看一下搜索机制:
事实证明,对于搜索,您需要以这种形式格式化 URL:
这里没有任何改变。
通过浏览器检查器检查结构
我们戳鼠标右键并选择Inspect Element:
一个面板将像这样打开:
我们研究并寻找视频的链接:
让我们尝试解析:
例如,让我们查找视频标签,例如
ytd-video-renderer:没有什么...
如果您寻找在检查员中看到的链接?
有趣...原来有一个链接,但它在错误的标签中。
让我们看看响应搜索请求的结果:
未找到标签
ytd-video-renderer...找到
ytd-video-renderer了,但它是在javascript中的А что насчет ссылки? Тоже в javascript (у меня сломался поиск в Page Source, поэтому показываю в Notepad++):
Получается, данные с поиском находятся в объекте, находящимся в
window["ytInitialData"]:Изучим window["ytInitialData"]Как видим из структуры, видео находятся в объектах videoRenderer
Теперь попробуем вытащить значение из
window["ytInitialData"]и обработать его.Для вытаскивания используем регулярное выражение, а для парсинга модуль json.
Как видим, данные успешно вытаскиваются, парсятся и обрабатываются:
Для удобства работы с словарем, я воспользуюсь модулем dpath.util, например так можно вытащить значения всех объектов с ключом videoRenderer:
Это все. Надеюсь, это было полезно 😄