处理更高级操作时(Cookies处理,代理设置),需要一个强大的工具Handler,可以理解成各种处理器,有处理登录认证的、有处理Cookies的、有处理代理设置的。利用这些几乎可以做到HTTP请求中所有事情。当中urllib.request模块里的 BaseHandler类是所有其他Handler的父类,提供了最基本的方法。如default_open()、protocol_request()等。
HTTPdefaultErrorHandler: 用于处理HTTP响应错误,错误会抛出HTTPError类型异常
HTTPRedirectHandler: 用于处理重定向
HTTPCookieProcessor: 用于处理Cookies
ProxyHandler: 用于设置代理,默认为空
HTTPPasswordMgr: 用于管理密码,维护了用户名和密码的表
HTTPBacisAuthHandler: 用于管理认证,弱一个链接打开需要认证,可以用它解决认证问题
代理ProxyHandler的使用:
代理的常用功能:
突破自身ip访问限制,访问国外站点。
访问一些单位或团体内部资源。
提高访问速度
通常代理服务器都设置一个较大的硬盘缓冲区,当有外界信息通过时,同时也将其保存到缓冲区。浏览器向代理服务器发出请求,当代理服务器接收请求信息号,再由代理服务器来取回浏览器所需要的信息并传送给终端用户的浏览器。
隐藏真实ip,免受攻击。
from http.client import HTTPResponse
from urllib import request
from urllib.request import ProxyHandler, Request
url = "http://httpbin.org/ip"
headers = [("User-Agent",
"Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/110.0.0.0 Safari/537.36")]
username = "YOUR_USERNAME"
password = "YOUR_PASSWORD"
ip = "YOUR_IP" # 例:127.0.0.1
port = 66666 # 例:30000
ip_port = f"{ip}:{port}"
handler = ProxyHandler({"http": f"http://{username}:{password}@{ip_port}"})
opener = request.build_opener(handler)
opener.addheaders = headers
response = opener.open(url) # type: HTTPResponse
print(response.read().decode("utf-8"))
另一个常用类OpenerDirector也叫Opener,urlopen()就可以看做是urllib提供的一个Opener。前面的Rquest和urlopen相当于类库封装好的常用的请求方法,可以完成基本的请求,但要实现更高级操作需要深入一层配置。所以需要用到Opener。
Cookies获取
CookieJar类的子类
CookieJar:管理HTTP cookie值、存储HTTP请求生成的cookie、向传出的HTTP请求添加cookie的对象。整个cookie都存储在内存中,对CookieJar实例进行垃圾回收后cookie也将丢失。
FileCookieJar:从CookieJar派生而来,用来创建FileCookieJar实例,检索cookie信息并将cookie存储到文件中。filename是存储cookie的文件名。delayload为True时支持延迟访问访问文件,即只有在需要时才读取文件或在文件中存储数据。
MozillaCookieJar:从FileCookieJar派生而来,创建与Mozilla浏览器 cookies.txt兼容的FileCookieJar实例。
LWPCookieJar:从FileCookieJar派生而来,创建与libwww-perl标准的 Set-Cookie3 文件格式兼容的FileCookieJar实例。
from http.client import HTTPResponse
from urllib import request, parse
from urllib.request import Request, HTTPCookieProcessor
from http.cookiejar import CookieJar
from io import BytesIO
import gzip
cookiejar = CookieJar()
login_url = "https://www.mac123.vip/ajax/login_h.jsp"
headers = {
"user-agent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/110.0.0.0 Safari/537.36"
}
data = "cmd=XXXXXXX_loginMember&encryptAcct=VVVVVVVVVVVVVV=&pwd=123456789000909090899089089089&captcha=&autoLogin=false"
req = Request(login_url, data=data.encode("utf-8"), headers=headers)
handler = HTTPCookieProcessor(cookiejar)
opener = request.build_opener(handler)
response = opener.open(req) # type: HTTPResponse
print(response.read().decode("utf-8"))
print(response.info().get_content_charset())
####################以下代码是查看登录信息的url的页面的获取#######################
info_url = "https://www.mac123.vip/mCenter.jsp"
info_req = Request(info_url, headers=headers)
info_response = opener.open(info_req) # type: HTTPResponse
data_bytes = info_response.read()
bytes = BytesIO(data_bytes)
f = gzip.GzipFile(fileobj=bytes)
print(f.read().decode("utf-8"))
备注:
获取登录信息的时候,https://www.mac123.vip/ajax/login_h.jsp的请求页面返回是压缩后的页面,需要gzip.GzipFile进行解压后进行解码操作。
CookieJar之cookie保存本地和读取:
cookie保存
from http.client import HTTPResponse
from urllib import request
from urllib.request import Request, HTTPCookieProcessor
from http.cookiejar import MozillaCookieJar
cookiejar = MozillaCookieJar("cookie.txt")
url = "http://httpbin.org/cookies/set/course/China"
headers = {
"user-agent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/110.0.0.0 Safari/537.36"
}
req = Request(url, headers=headers)
handler = HTTPCookieProcessor(cookiejar)
opener = request.build_opener(handler)
response = opener.open(req) # type: HTTPResponse
print(response.read().decode("utf-8"))
cookiejar.save()
发现读取不到,原因是因为该接口设置的cookie仅浏览时存储。
解决方法是:
cookiejar.save()
将两个参数设置为True,即可解决!!!
from http.client import HTTPResponse
from urllib import request
from urllib.request import Request, HTTPCookieProcessor
from http.cookiejar import MozillaCookieJar
cookiejar = MozillaCookieJar("cookie.txt")
url = "http://httpbin.org/cookies/set/course/China"
headers = {
"user-agent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/110.0.0.0 Safari/537.36"
}
req = Request(url, headers=headers)
handler = HTTPCookieProcessor(cookiejar)
opener = request.build_opener(handler)
response = opener.open(req) # type: HTTPResponse
print(response.read().decode("utf-8"))
cookiejar.save(ignore_discard=True, ignore_expires=True)