数据采集——python3.xpath.urllib[*]

1.入门程序

爬虫采集数据,主要采集网站数据,通常情况下操作步骤如下:
1)确定目标网站url地址
2)对目标url地址发送请求
3)获取网站返回的响应数据‘
4)对响应数据进行解析处理
5)得到目标数据

具体代码如下

# -*- coding: utf-8 -*-

# 引入爬虫程序依赖的模块
from urllib import request

# 定义要采集数据的目标地址
target_url = "http://www.sina.com"

# 向服务器发送请求,获取服务器的响应数据
response = request.urlopen(target_url)

# 展示获取到的数据
html = response.read()
print(html.decode("utf-8"))

2.数据编码处理

我们通过爬虫程序可以得到网站返回的数据,但是返回的数据在展示的过程中,出现了乱码,这是因为网站本身有自己的字符编码,而我们的程序在数据采集完成后在控制台展示的过程中使用的是本地默认的编码,由于编码的不一致,导致了乱码的产生。
网页中的编码一般会定义在<meta charset=''>标签中。所以爬虫采集网页数据是可以分为两个步骤进行操作,先采集批量网页中的一个网页查看编码格式,然后在代码中使用指定的格式进行解码,得到正确的数据后,再进行批量网页数据的采集,这就是手工指定编码方式

3.使用urllib

3.1 url概述

urllib库是python内置的HTTP请求库,不需要额外安装即可使用。它包含四个模块:

1)request: 它是最基本的HTTP请求模块,可以用来模拟发送请求,只需要给库方法传入url以及额外的参数,就可以模拟实现浏览器输入网址敲回车的过程了

2)error: 异常处理模块,如果请求出现错误,我们可以捕获这些异常,进行重试或其他操作保证进程不会终止

3)parse: 一个工具模块,提供了许多url方法,比如拆分、解析、合并等

4)robotparser: 主要用来识别网站的tobots.txt文件,判断网站是够可爬,使用较少

3.2发送请求

使用urllib的request模块,可以实现发送请求并返回响应

3.2.1ulopen()

urllib.request模块提供了最基本的构造HTTP请求方法,利用它可以模拟浏览器的一个请求发起过程,同时它还带有处理授权验证、重定向、浏览器cookies以及其他内容

import urllib.request
response= urllib.request.urlopen( ' https://www.python.org')
pri 1t(response. read(). decode (’ utf-8')) 

传参:

1)data参数
data参数是可选的,如果需添加该参数且是bytes类型,则需通过bytes()方法转化。若传递此参数,则其请求方式由GET请求变为POST请求

import urllib.parse
import urllib.request
data = bytes(urllib . parse . urlencode({'word ’:’ hello'}), encoding =’ ut 8')
response= urllib.request.urlopen('http://httpbin.org/post ’, data=data)
print(response.read()) 

次数传递参数为Word,值为hello。需被转化为bytes类型,需要用 urllib.parse
块里的 urlencode ()方法来将参数字典转化为字符串;第 个参数指定编码格式,这里指定为 utf8,这里请求的站点是 httpbin .org ,它可以提供 HTTP 请求测试 本次我们请求的 URL http :// httpbin.org/ post ,这个链接可以用来测试 POST 请求,它可以输出请求的一些信息 ,其中包含我们传递的 data参数。运行结果如下

{
    "args" : {},
    ”data ”:,
    "files”. {}, ”form”:
           { “word ":”hello”
      },
      "headers " {
            “ Accept-Encoding ":”identity”,
             “ Content-Length”: '’ 10”, 
              ”Content ype ":"application/x-www-form-urlencoded",
              "Host ”:” httpb n.org ”,
              ”User-Agent"”Python-urllib/3. 5"
              ’' j son ”: null ,
              ”origin '’,” 123.124.23.253 ”,
              "url”:”http://httpbin.org/post" 
}

传递的参数出现在了from字段中,表名模拟了表单的提交方式,以post请求传递数据

2)timeout参数

timeout参数用于设置超时时间,单位为秒。若请求超出了设置的这个时间还没有得到响应,则会抛出异常,若不指定该参数,就会使用全局默认时间,它支持HTTP、HTTPS、FTP请求。可以通过设置这个超时时间来控制一个网页,若长时间未响应,则跳过其抓取

3)其他参数
除了 data 参数和 timeout 参数外,还有 context 参数,它必须是 ssl.SSLContext 类型,用来指定SSL。此外, cafile ca path 这两个参数分别指定 CA 证书和它的路径,这个在请求 HTTPS 链接时有用,cadefault 参数现在已经弃用了,其默认值为 False

3.2.2 request

利用urlopen()方法可以实现最基本请求的发起,但这几个简单的参数并不足以构造一个请求。如果请求中需要加入headers等信息,则需要用更加强大的request请求进行构建。request用法如下:

import urllib .request
request = urllib.request.Request(’ https://python .org')
response = urllib .request.urlopen(request)
print(response.read().decode (’ utf-8')) 

此处依然用urlopen()方法发送请求,但参数却由url变为request类型的对象,通过构造这个数据结构,一方面可以将请求独立成一个对象,另一个方面可以更加灵活地配置参数。request参数构造方法如下:

class urllib. request. Request ( ur 1, data=None, headers={}, origin_req_host=None, unverifiable=False, method=None) 

齐总第一个参数url用于请求URL,为必填参数,其他都是可选参数

第二个参数data如果要传,必须要传types类型的,若它是字典,可先用urllib.parse模块中的urlencode()编码

第三个参数headers是一个字典,它就是请求头,我们可以在构造请求时通过headers参数直接构造,也可以通过调用请求实例的add_header()方法添加

第四个参数orgin_req_host指的是请求方的host或IP地址

第五个参数unverifiable表示这个请求是否无法验证的,默认是false,表示用户没有足够权限来接收这个请求

第六个参数method是一个字符串,用来指示请求的使用方法

3.2.3 高级用法

在上面的过程中,我们虽然可以构造请求,但对于更加高级的一些操作无法实现,此时就需要handler大展雄姿了。我们可以把handler理解为各种处理器,有专门验证登录的,有处理cookies的,有处理代理设置的,利用它们,我们几乎可以做到HTTP请求中的所有事情。

首先,介绍一下urllib.request模块中的basehandler类,它是所有其他handler的父类,提供了最基本的方法。另外一个比较重要的类就是openerdirector,我们可以成为opener,之前用过的urlopen()方法,实际上就是urllib为我们提供的额一个opener。之所以引入opener,是因为需要实现更加高级的功能。之前使用的request和urlopen()相当于类库为你封装好了及其常用的请求方法,利用它们可以完成基本的请求。但现在需要实现更加高级的功能,所以需要深入一层进行配置,使用能更加底层的实例来完成操作,所以这里用到了opener。

opener可以使用open()方法,返回的类型和urlopen()如出一辙,它与handler的关系简而言之就是利用handler来构建opener

1)代理
在做爬虫时,可能会由于短时间内造成服务器压力而被认定为恶意攻击从而导致IP地址封禁,从而导致IP地址不可用。为了避免此类情况的发生,我们可以使用代理。添加代理方法如下:

from urllib.error import URLError
from urllib.request import ProxyHandler, build opener
proxy _handler = ProxyHandler({
’ http ':’http://127.o.o .1:9743 ’,
’ https’:’https://127.0 .0.1:9743 ’
})
opener = build_opener(proxy_handler)
try:
response = opener.open (’ https://www.baidu.com')
print(response.read() .decode (’ utf-8'))
except URLError as e:
print(e .reason) 

2)cookies
cookies的处理需要相关的handler,将网站cookies获取下来的代码如下:

import http .cookiejar, urllib.request
cookie = http. cookie jar. CookieJar()
handler = urllib .request.HTTPCookieProcessor (cookie)
opener = urllib.request . build opener(handler )
response = opener. open (’ http://www.baidu.com')
or item in cookie:
print(item.name+”=”+item.value) 

4.处理异常

异常可能会导致程序因报错而终止,因此异常的处理是十分必要的。urllib的error模块定义了由request模块产生的异常,若果出现了问题,request模块便会跑出error模块定义的异常

4.1 urlerror

1)urlerror类来自urllib库的error模块,它继承自oserroe类,是error异常模块的基类,由request模块产生的异常都可以通过这个类来进行捕获

2)HTTPerror

它是URLerror的子类,专门用来处理HTTP请求错误,比如认证请求失败等等。它有如下三个属性:

code :返回HTTP状态码

reason:同父类一样用于返回错误的原因

headers:返回请求头

4.2 解析链接

1)urlparse()
该方法可以实现URL的识别和分段。一个标准的url都会符合规则,利用urlparse()方法将其拆分下来,即:

解析时有特定的分隔符
比如,://前面的就是 scheme ,代表协议;第一个/符号前面便是 netloc ,即域名,后面是 path ,即访
问路径;分号;前面是 pa rams ,代表参数;问号?后面是查询条件 query 般用作 GET 类型的 URL;
井号#后面是锚点,用于直接定位页面内部的下拉位置

它有三个参数:

urlstring:这是必填项,即待解析的URL

scheme:它是默认的协议,加入这个链接没有带协议信息,会将这个作为默认的协议

allow_fragments:即是否忽略fragment,如果它被设置为false.fragment部分就会被忽略,它会被解析为path、parametes或者query的一部分,而fragment部分为空

2)urlunparse()

有了urlparse(),相应的就有了它的队里方法urlunparse。它接收的参数是一个可迭代对象,但长度必须为6,否则会抛出参数数量不足或过多的问题

3)urlsplit()

这个方法和urlparse()方法非常相似,只不过它不再单独解析params这一部分,只返回五个结果。

4) urlunsplit()
urlunparse ()类似,它也是将链接各个部分组合成完整链接的方法,传人的参数也是一个可迭代对象,例如列表 元组等,唯 的区别是长度必须为5

5)urljoin()
有了 urlunparse ()和 urlu isplit ()方法,我们可以完成链接的合井,不过前提必须要有特定长度的对象,链接的每一部分都要清晰分开。此外,生成链接还有另 个方法,那就是 urljoin ()方法 我们可以提供一个 base_url (基础链接)作为第1 个参数,将新的链接作为第二个参数,该方法会分析 base_url 的scheme、 netloc和 path这3个内容并对新链接缺失的部分进行补充,最后返回结果

6) urlencode()
这个方法非常常用有时为了更加方便的构造参数,我们会事先用字典来表示,要转化为url的参数时,只需要调用该方法即可

7) parse_qs()
有了序列化,必然就有反序列化 如果我们有一串 GET 请求参数,利用 parse qs ()方法, 就可以将它转回字典

8)parse_qsl()
另外,还有 parse_qs ()方法,它用于将参数转化为元组组成的列表

9)quote()
该方法可以将内容转化为 URL 编码的格式 URL 中带有中文参数时,有时可能会导致乱码的问题,此时用这个方法可以将巾文字符转化为 RL 编码

10)unquote()
有了 quote ()方法,当然还有 unquote ()方法,它可以进行 URL 解码

5.分析robots协议

利用 urllib的 robot parser 模块,我们可以实现网站 Ro 协议的分析

1)robots协议
Robots 协议也称作爬虫协议、机器人协议,它的全名叫作网络爬虫排除标准( Robots ExclusionProtocol ),用来告诉爬虫和搜索引擎哪些页面可以抓取,哪些不可以抓取 它通常是一个叫作 ro bots .txt的文本文件,一般放在网站的根目录下。当搜索’爬虫访问一个站点时,它首先会检查这个站点根目录下是否存在 ro ots.txt 文件,如果存在,搜索爬虫会根据其中定义的爬取范围来爬取 如果没有找到这个文件,搜索爬虫便会访问所有可直接访问的页面

2)robotparser
该模块提供了一个类robotfileparser,
它可以根据某网站的robot.txt文件来判断一个爬去爬虫是否有权限来爬去这个网页,该类使用只需要在构造方法里传入robots.txt的链接即可。常用方法:

set_url():用来设置robots.txt文件的链接,如果在创建robotfileparser对象时传入了链接,那么就不需要再使用该方法设置

read():读取robots.txt文件并进行分析。该方法执行一个读取和分析操作,如果不调用该方法,接下来的判断都会为false,所以一定得调用,这个方法不会反悔任何内容,但是执行了读取操作

3)parse():用来解析robots.txt文件,传入的参数是robots.txt某些行的内容,它会按照robots.txt的语法规则来分析这些内容

4)can_fetch():该方法传入两个参数,第一个是user—agent,第二个是要抓取的url。返回的内容是该搜索引擎是否可以抓取这个url,返回的结果是True或False

5)mtime():返回的是上次抓取和分析robots.txt的时间,这对于长时间分析和抓取的搜索爬虫是很有必要的,可能会需要定期检查来抓取最新的robots.txt

6)modified():它同样对长时间分析和抓取的搜索爬虫很有帮助,将当前时间设置为上次抓取和分析robots.txt的时间

©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 194,242评论 5 459
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 81,769评论 2 371
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 141,484评论 0 319
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 52,133评论 1 263
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 61,007评论 4 355
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 46,080评论 1 272
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 36,496评论 3 381
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 35,190评论 0 253
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 39,464评论 1 290
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 34,549评论 2 309
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 36,330评论 1 326
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 32,205评论 3 312
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 37,567评论 3 298
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 28,889评论 0 17
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 30,160评论 1 250
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 41,475评论 2 341
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 40,650评论 2 335

推荐阅读更多精彩内容