在Python中完成渲染后,如何刮取网页的HTML内容

在Python中完成渲染后,如何刮取网页的HTML内容,python,html,beautifulsoup,rendering,Python,Html,Beautifulsoup,Rendering,我目前的任务是搜集流行笑话网站。一个例子是一个名为。如果您访问该网站,将光标短暂地悬停在页面左侧的“获取随机笑话”按钮上方,您会注意到它重定向到的链接将是crooks.cc.com/# 如果您等待一段时间,它将变为网站中显示实际笑话的适当链接。它变为crooks.cc.com/*合法笑话链接* 如果您分析页面的HTML,您会注意到有一个链接()带有class=random\u link,其存储指向页面要重定向的随机链接。您可以在页面完全加载后进行检查。基本上,“#”被合法链接取代 现在,这里是我

我目前的任务是搜集流行笑话网站。一个例子是一个名为。如果您访问该网站,将光标短暂地悬停在页面左侧的“获取随机笑话”按钮上方,您会注意到它重定向到的链接将是
crooks.cc.com/#

如果您等待一段时间,它将变为网站中显示实际笑话的适当链接。它变为
crooks.cc.com/*合法笑话链接*

如果您分析页面的HTML,您会注意到有一个链接(
)带有
class=random\u link
,其
存储指向页面要重定向的随机链接。您可以在页面完全加载后进行检查。基本上,“#”被合法链接取代

现在,这里是我的代码,用于删除HTML,就像我到目前为止对静态网站所做的那样。我使用了
beautifulsou
库:

import urllib
from bs4 import BeautifulSoup

urlToRead = "http://jokes.cc.com";
handle = urllib.urlopen(urlToRead)
htmlGunk =  handle.read()
soup = BeautifulSoup(htmlGunk, "html.parser")
# Find out the exact position of the joke in the page
print soup.findAll('a', {'class':'random_link'})[0]
输出:#

这是预期的输出,因为我已经意识到页面尚未完全呈现

等待一段时间后,或渲染完成后,如何刮取页面。我需要使用像Mechanize这样的外部库吗?我不确定如何做到这一点,因此非常感谢您的帮助/指导

编辑:通过在Python中使用PhantomJS和Selenium,我终于能够解决我的问题。下面是渲染完成后获取页面的代码

from bs4 import BeautifulSoup
from selenium import webdriver


driver = webdriver.PhantomJS() #selenium for PhantomJS
driver.get('http://jokes.cc.com/')
soupFromJokesCC = BeautifulSoup(driver.page_source) #fetch HTML source code after rendering
# locate the link in HTML
randomJokeLink = soupFromJokesCC.findAll('div', {'id':'random_joke'})[0].findAll('a')[0]['href']
# now go to that page and scrape the joke from there
print randomJokeLink #It works :D

您要查找的数据是由页面加载时动态运行的JavaScript生成的。BeautifulSoup没有JavaScript引擎,因此无论您等待多长时间,链接都不会更改。有一些Python库可以学习和理解JavaScript,但是你最好的选择可能是挖掘并弄清楚网站上的JS实际上是如何工作的。例如,如果他们有一个随机笑话的笑话数据源,它可能是一种类似JSON的格式,Python可以很容易地解析这种格式。这将使您的应用程序比包含一个成熟的脚本引擎要轻量级得多。

selenium浏览器自动化是一种可行的方法吗?注意,我从未使用过selenium,但这取决于您的项目范围。如果您正在编写一个显示笑话的应用程序,那么自动化web浏览器可能并不理想。这将需要用户安装并打开浏览器,最终会将大量工作转移到浏览器上。但是,如果你深入研究JavaScript的工作原理,你可以在应用程序中重新创建行为,甚至不需要考虑JavaScript就可以取笑别人。使用无头浏览器怎么样?我使用PhantomJS和Selenium解决了这个问题。看看更新的描述