2015-09-26 52 views
0

我想爬(轻轻地)一个网站,并下载我抓取的每个HTML页面。为了实现这一点,我使用库请求。我已经完成了抓取列表,并尝试使用urllib.open抓取它们,但是没有用户代理,我收到一条错误消息。所以我选择使用请求,但我不知道如何使用它。Python爬行器:下载HTML页面

headers = { 
    'User-Agent': 'Mozilla/5.0 (X11; Linux x86_64; rv:2.0.1) Gecko/20100101 Firefox/4.0.1' 
} 
page = requests.get('http://www.xf.com/ranking/get/?Amount=1&From=left&To=right', headers=headers) 
with open('pages/test.html', 'w') as outfile: 
    outfile.write(page.text) 

问题是,当脚本尝试写在我的文件中的回应,我得到一些编码错误:

UnicodeEncodeError: 'ascii' codec can't encode characters in position 6673-6675: ordinal not in range(128) 

我们如何写在一个文件,而无需那些编码问题?

回答

2

在Python 2,文本文件不接受Unicode字符串。使用response.content访问原始二进制,未解码的内容:

with open('pages/test.html', 'w') as outfile: 
    outfile.write(page.content) 

这将写入所下载的HTML原编码由网站提供服务。

另外,如果你想重新编码到一个特定编码的所有响应,使用io.open()从而产生不接受Unicode的文件对象:

import io 

with io.open('pages/test.html', 'w', encoding='utf8') as outfile: 
    outfile.write(page.text) 

注信令在正确的编解码器,很多网站需要HTML标签,并且内容可以在没有字符集参数的情况下被提供。

在这种情况下requests使用默认编解码器的MIME类型text/*,拉丁-1,HTML解码为Unicode文本。 这通常是错误的编解码器并依靠此行为可以导致以后输出Mojibake。我建议你坚持编写二进制内容,并依靠像BeautifulSoup这样的工具来稍后检测正确的编码。

可替代地,测试明确地为charset参数存在,只有重新编码(通过response.textio.open()或其他)如果requests不降回Latin-1的默认值。请参阅retrieve links from web page using python and BeautifulSoup获取答案,我使用这种方法告诉BeautifulSoup使用哪种编解码器。

0
outfile.write(page.text.encode('utf8', 'replace')) 

我发现的文件就在这里:unicode problem

+1

UTF-8编码解码器可以编码所有的Unicode标准,“替换”错误处理程序在这里是多余的,因为它永远不会被需要。 –