如果浏览器不支持帧+如何直接获取帧的内容,则无法直接访问帧

时间:2014-07-19 14:51:44

标签: python web-scraping html-parsing beautifulsoup mechanize

我正在尝试从this等网址自动下载PDF,以建立联合国决议图书馆。

如果我使用漂亮的汤或机械化打开该URL,我会得到"您的浏览器不支持框架" - 如果我在chrome dev工具中使用副本作为curl功能,我会得到同样的东西。

"您的浏览器的标准建议不支持框架"当使用机械化或美丽的汤时,要遵循每个单独框架的来源并加载该框架。但是,如果我这样做,我会收到一条错误消息,指出该页面不是authorized

我该怎么办?我想我可以在僵尸或幻像中尝试这个,但我宁愿不使用这些工具,因为我不熟悉它们。

1 个答案:

答案 0 :(得分:4)

好的,这是一项与requestsBeautifulSoup有关的有趣任务。

un.orgdaccess-ods.un.org的一系列基础调用很重要,并设置了相关的Cookie。这就是为什么您需要维护requests.Session()并访问几个网址才能访问pdf。

这里是完整的代码:

import re
from urlparse import urljoin

from bs4 import BeautifulSoup
import requests


BASE_URL = 'http://www.un.org/en/ga/search/'
URL = "http://www.un.org/en/ga/search/view_doc.asp?symbol=A/RES/68/278"
BASE_ACCESS_URL = 'http://daccess-ods.un.org'

# start session
session = requests.Session()
response = session.get(URL, headers={'User-Agent': 'Mozilla/5.0 (Macintosh; Intel Mac OS X 10_9_4) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/35.0.1916.153 Safari/537.36'})

# get frame links
soup = BeautifulSoup(response.text)
frames = soup.find_all('frame')
header_link, document_link = [urljoin(BASE_URL, frame.get('src')) for frame in frames]

# get header
session.get(header_link, headers={'Referer': URL})

# get document html url
response = session.get(document_link, headers={'Referer': URL})
soup = BeautifulSoup(response.text)

content = soup.find('meta', content=re.compile('URL='))['content']
document_html_link = re.search('URL=(.*)', content).group(1)
document_html_link = urljoin(BASE_ACCESS_URL, document_html_link)

# follow html link and get the pdf link
response = session.get(document_html_link)
soup = BeautifulSoup(response.text)

# get the real document link
content = soup.find('meta', content=re.compile('URL='))['content']
document_link = re.search('URL=(.*)', content).group(1)
document_link = urljoin(BASE_ACCESS_URL, document_link)
print document_link

# follow the frame link with login and password first - would set the important cookie
auth_link = soup.find('frame', {'name': 'footer'})['src']
session.get(auth_link)

# download file
with open('document.pdf', 'wb') as handle:
    response = session.get(document_link, stream=True)

    for block in response.iter_content(1024):
        if not block:
            break

        handle.write(block)

您可能应该将单独的代码块提取到函数中,以使其更具可读性和可重用性。

仅供参考,在seleniumGhost.py的帮助下,通过真实的浏览器可以更轻松地完成所有这些工作。

希望有所帮助。