Python 爬虫入门(一)urllib的基本使用
参考资料:
1.用python开发爬虫 https://www.gitbook.com/book/germey/python3webspider/details
2.论一只爬虫的自我修养 http://blog.fishc.com/category/python/spider
3.Python爬虫学习系列教程 http://cuiqingcai.com/1052.html
4.Beautiful Soup 4.2.0 中文文档 https://wizardforcel.gitbooks.io/bs4-doc/content/
5.Requests: 让 HTTP 服务人类 http://docs.python-requests.org/zh_CN/latest/
前言:
urllib包含四个模块:
- urllib.request可以用来发送request和获取request的结果
- urllib.error包含了urllib.request产生的异常
- urllib.parse用来解析和处理URL
- urllib.robotparse用来解析页面的robots.txt文件
1. urllib.request的基本使用方法属性
1.1. 使用urllib.request.urlopen()来爬取网页
In [1]: import urllib.request In [2]: r=urllib.request.urlopen('http://blog.fishc.com/3597.html') In [3]: r.read().decode('utf-8') Out[3]: 'nnn
论一只爬虫的自我修养2:实战 – 零基础入门学习Python054 | 鱼C工作室 nnn使用urllib.error处理异常.
这里主要了解下try
,except
用法:import urllib.request import urllib.error try: response=urllib.request.urlopen('http://suibiankankan.com') except urllib.error.URLError as e: print(e.reason) # [Errno -2] Name or service not known
3. 使用urllib.parse解析链接
使用
urllib.parse.urlparse()
进行链接解析,拆解链接的各部分内容。In [17]: import urllib.parse In [19]: result = urllib.parse.urlparse('http://www.baidu.com/index.html;user?id=5#comment') In [20]: type(result) Out[20]: urllib.parse.ParseResult In [21]: result Out[21]: ParseResult(scheme='http', netloc='www.baidu.com', path='/index.html', params='user', query='id=5', fragment='comment') In [22]: result[1] Out[22]: 'www.baidu.com' In [24]: result.netloc Out[24]: 'www.baidu.com'
观察可以看到,返回结果是一个ParseResult类型的对象,它包含了六个部分,分别是
scheme
、netloc
、path
、params
、query
、fragment
。使用索引或者属性可以查看解析结果。
由上可以得出一个标准的链接格式如下:scheme://netloc/path;parameters?query#fragment
使用urllib.parse.urlunparse()可以将几个部分连接起来。
In [25]: data = ['http', 'www.baidu.com', 'index.html', 'user', 'a=6', 'comment'] In [26]: urllib.parse.urlunparse(data) Out[26]: 'http://www.baidu.com/index.html;user?a=6#comment'
其他的一些方法:
(1)urllib.parse.urlsplit()
,这个和urlparse()方法非常相似,只不过它不会单独解析parameters这一部分,只返回五个结果。上面例子中的parameters会合并到path中。
(2)urllib.parse.urlunsplit()
,与urlunparse()类似,也是将链接的各个部分组合成完整链接的方法,传入的也是一个可迭代对象。 例如list、tuple等等,唯一的区别是,长度必须为5。
(3)urllib.parse.urljoin()
,利用urljoin()方法我们可以提供一个base_url(基础链接),新的链接作为第二个参数,方法会分析base_url的scheme、netloc、path这三个内容对新链接缺失的部分进行补充,作为结果返回。如果这三项在新的链接里面不存在,那么就予以补充,如果新的链接存在,那么就使用新的链接的部分。base_url中的parameters、query、fragments是不起作用的。In [27]: urllib.parse.urljoin('http://www.baidu.com', 'FAQ.html') Out[27]: 'http://www.baidu.com/FAQ.html'
4. 使用urllib.robotparser分析robots协议
robots协议也被称作爬虫协议、机器人协议,它的全名叫做网络爬虫排除标准(Robots Exclusion Protocol),同来告诉爬虫和搜索引擎哪些页面可以抓取,哪些不可以抓取。它通常是一个叫做robots.txt的文本文件,放在网站的根目录下。
当一个搜索蜘蛛访问一个站点时,它首先会检查下这个站点根目录下是否存在robots.txt文件,如果存在,搜索蜘蛛会根据其中定义的爬取范围来爬取。如果没有找到这个文件,那么搜索蜘蛛便会访问所有可直接访问的页面。User-agent: * Disallow: / Allow: /public/
以上的两行实现了对所有搜索蜘蛛只允许爬取public目录的作用。
如上简单的两行,保存成robots.txt文件,放在网站的根目录下,和网站的入口文件放在一起。比如index.php、index.html、index.jsp等等。
那么上面的User-agent就描述了搜索蜘蛛的名称,在这里将值设置为*,则代表该协议对任何的爬取蜘蛛有效。比如你可以设置User-agent: Baiduspider,就代表我们设置的规则对百度搜索引擎是有效的。如果有多条User-agent记录,则就会有多个爬取蜘蛛会受到爬取限制,但你至少需要指定一条。
Disallow指定了不允许抓取的目录,比如上述例子中设置为/则代表不允许抓取所有页面。
Allow它一般和Disallow一起使用,一般不会单独使用,现在我们设置为/public/,起到的作用是所有页面不允许抓取,但是public目录是可以抓取的。urllib.robotparser提供了一个类,叫做RobotFileParser。它可以根据某网站的robots.txt文件来判断一个爬取蜘蛛是否有权限来爬取这个网页。
使用方法:urllib.robotparser.RobotFileParser(url='')
例子:
rom urllib.robotparser import RobotFileParser rp = RobotFileParser('http://www.jianshu.com/robots.txt') rp.read() print(rp.can_fetch('*', 'http://www.jianshu.com/p/b67554025d7d')) print(rp.can_fetch('*', "http://www.jianshu.com/search?q=python&page=1&type=collections")) # True # False
以上简单介绍urllib的简单用法,下面给出一个实战例子,交互式有道翻译请求:
import urllib.request import urllib.parse import json url = 'http://fanyi.youdao.com/translate?smartresult=dict&smartresult=rule&smartresult=ugc&sessionFrom=https://www.google.com.hk/' data=dict() data['type']='AUTO' data['i']=input("Plz input what you want to translate: ") data['doctype']='json' data['xmlVersion']='1.8' data['keyfrom']='fanyi.web' data['ue']='UTF-8' data['action']='FY_BY_CLICKBUTTON' data['typoResult']='true' data=urllib.parse.urlencode(data).encode('utf-8') # 必须对data进行转码 response=urllib.request.urlopen(url,data) html=response.read().decode('utf-8') target=json.loads(html) print('翻译结果:',target['translateResult'][0][0]['tgt'])
文章来源于互联网:Python 爬虫入门(一)urllib的基本使用