需要的模块
urllib.request
获取get一个请求
这里以百度为例
r = urllib.request.urlopen("http://www.baidu.com")
获取之后我们输出r可以发现r是一个对象
<http.client.HTTPResponse object at 0x000002AE92E36040>
可以使用read()方法将该对象内容读出来,这里只截取一部分
b'<!DOCTYPE html><!--STATUS OK--><html><head><meta http-equiv="Content-Type" content="text/html;charset=utf-8"><meta http-equiv="X
可以使用read().decode("utf-8")对上述内容进行解码,解码完毕后就是html代码了
把这些内容粘贴到txt文件里,把文件类型改为html,之后打开,会发现跟百度一模一样
获取一个post请求
可以使用这个网站来测试post请求,httpbin.org
我们使用这个HTTP Methods
点击post后,点try it out
再点击这个execute,就相当于我们访问了这个网站,他返回的信息 ,就出现了
返回的信息为
上面使html代码,包含我们的访问方式,使用的浏览器的版本等等,这个Use-Agent就是使用的浏览器版本
就是说post请求,是当我们就收到一部分信息后,在我们做出反应后,服务器才会将剩下的东西发给我们
如何用python获取一个post请求呢?
具体做法如下,
import urllib.request
import urllib.parse
#由于urllib.request.urlopen 中data参数必须是一个字节对象、可迭代对象,所以要转格式,这里将信息转 #为可迭代对象
#封装信息,并将封装好的信息转换为字节对象,
data = bytes(urllib.parse.urlencode({"heallo":"world"}),encoding = "utf-8")
#/post就代表获取post请求,data是附加信息
r = urllib.request.urlopen("http://httpbin.org/post",data = data)
'''
也可以用
r = urllib.request.urlopen("http://httpbin.org",data = data,method ="POST")
输出结果
print(r.read().decode("utf-8"))
urllib.request.urlopen函数原型如下:urllib.request.urlopen(url, data=None, [timeout, ]*, cafile=None, capath=None, cadefault=False, context=None)
<1>url是目标资源在网路中的位置。可以是一个表示URL的字符串(如:http://www.xxxx.com/);也可以是一个urllib.request对象
<2>data用来指明发往服务器请求中的额外的信息(如:在线翻译,在线答题等提交的内容)。HTTP是python中实现的众多网络通信http、https、ftp等协议中,唯一一个 使用data 参数的,也就是说只有打开的是http网址的时候,自定义data参数才会有作用。另外,官方API手册介绍指出:
- data必须是一个字节数据对象(Python的bytes object)
- data必须符合标准the standard application/x-www-form-urlencoded format,怎么得到这种标准结构的data呢?使用urllib.parse.urlencode()将自定义的data转换成标准格式,而这个函数所能接收的参数类型是pyhon中的mapping object(键/值对,如dict) or a sequence of two-element tuples(元素是tuple的列表)。
- data也可以是一个可迭代的对象,这种情况下就需要配置response对象中的Conten-length,指明data的大小。
- data默认是None,此时以GET方式发送请求;当用户给出data参数的时候,改为POST方式发送请求。
<3>cafile、capath、cadefault 参数:用于实现可信任的CA证书的HTTP请求。(基本上很少用)
<4>context参数:实现SSL加密传输。(基本上很少用)
输出结果为
{
"args": {},
"data": "",
"files": {},
"form": {
"heallo": "world"
},
"headers": {
"Accept-Encoding": "identity",
"Content-Length": "12",
"Content-Type": "application/x-www-form-urlencoded",
"Host": "httpbin.org",
"User-Agent": "Python-urllib/3.8",
"X-Amzn-Trace-Id": "Root=1-5ead4267-7ae21e305363f551481d4195"
},
"json": null,
"origin": "xxx.xxx.xxx.xx",#ip
"url": "http://httpbin.org/post"
}
这个form就是我们给服务器发送的内容
这一点可以说明,如果有需要用户登录的网站,可以使用post的方式,将用户名和密码发过去
还有一点就是,在返回的信息里,User-Agent里显示的是python,说明我们是以python浏览的这个网页,某些网站会根据这个User-Agent来判断是否是爬虫,比如说豆瓣
如果我们直接获取一个get请求
import urllib.request
url ='https://www.douban.com'
r = urllib.request.urlopen(url)
print(r.read())
输出为
File "E:\学习\lib\urllib\request.py", line 502, in _call_chain
result = func(*args)
File "E:\学习\lib\urllib\request.py", line 649, in http_error_default
raise HTTPError(req.full_url, code, msg, hdrs, fp)
urllib.error.HTTPError: HTTP Error 418:
这个418就是说明,豆瓣根据User-Agent发现了你是一个爬虫
所以我们要进行伪装
我们手动浏览豆瓣,找到我们的user-Agent
#创建一个字典来存我们手动浏览时候的浏览器信息
headers ={
"User-Agent":"Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/69.0.3497.100 Safari/537.36"
}
#目标网站
url ="https://www.douban.com"
我们需要一个方法把,headers信息封装进去
req = urllib.request.Request(url =url,headers =headers)
封装完之后,直接使用这个req对象
r = urllib.request.urlopen(req)
print(r.read().decode("utf-8"))
为什么urllib.request.urlopen可以使用req呢?
因为它的url参数可以是一个string类型也可以是一个Request的对象
这时候就有输出了
输出结果仅展示部分
11655 个成员
</div>
<li>
<div class="pic">
<a href="https://www.douban.com/group/402725/"><img src="https://img3.doubanio.com/f/shire/a1fdee122b95748d81cee426d717c05b5174fe96/pics/blank.gif" data-origin="https://img1.doubanio.com/view/group/sqxs/public/17fdb616ff143d8.jpg" alt="" width="48" /></a>
</div>
<div class="info">
<div class="title">
<a href="https://www.douban.com/group/402725/">记事本圆梦小组</a>