1.urllib库的使用
urllib.request.rulopen()模拟浏览器向服务器发送请求
response 服务器返回的数据
response的数据类型是HttpResponse
字节-->字符串
解码decode
字符串-->字节
编码encode
#使用urllib来获取百度首页的源码
import urllib.request
#1.定义一个url 就是要访问的地址
url = 'http://www.baidu.com'
#2.模拟浏览器向服务器发送请求(需要联网) response=响应
response=urllib.request.urlopen(url)
#3.获取响应中的页面源码 content内容的意思
#read方法 返回的是字节式的二进制数据
#我们要将二进制数据转换为字符串
#二进制-->字符串 解码 decode('编码的格式')
content=response.read().decode('utf-8') #这一步非常重要
#4.打印数据
print(content)
read() 字节形式读取二进制 扩展:rede(5)返回前几个字节
readline() 读取一行
readlines() 一行一行读取 直至结束
getcode() 获取状态吗
geturl() 获取url
getheaders() 获取headers
urllib.request.urlretrieve()
import urllib.request
url='http://www.baidu.com'
#模拟浏览器向服务器发送请求
response=urllib.request.urlopen(url)
#一个类型和六个方法
# response 是HTTPResponse的类型
print(type(response))
#按照一个字节一个字节去读
# content=response.read()
# print(content)
#返回多少个字节
# content = response.read(5) #只读五个字节
# print(content)
# #只读取一行
# content = response.readline()
# print(content)
# #读取多行
# content = response.readlines()
# print(content)
# #获取状态码 如果是200了,那么就证明我们的逻辑没有错
# print(response.getcode())
#
# #返回url地址
# print(response.geturl())
#
# #获取是一个状态信息
# print(response.getheaders())
#一个类型 HTTTPResponse
#六个方法 read readline readlines getcode geturl getheaders
请求页面
请求图片
请求视频
import urllib.request
#下载网页
url_page='http://www.baidu.com'
# url代表的是下载的路径 filename文件的名字
# 在python中 可以变量的名字,也可以直接写值
# urllib.request.urlretrieve(url_page,'baidu.html')
#下载图片
# url_img='https://image.so.com/view?src=imageonebox&q=LISA&obx_type=360pic_new_strong&correct=LISA&ancestor=list&cmsid=9cc840c2046491a3c774ae2f7fa315f4&cmras=0&cn=0&gn=0&kn=50&crn=0&bxn=0&fsn=110&cuben=0&pornn=0&manun=50&adstar=0&clw=241#id=8bc223c645b45b276ae559e1ab81c72f&currsn=0&ps=129&pc=129'
# urllib.request.urlretrieve(url=url_img, filename='lisa.png')
#下载视频
2.请求对象的定制
爬虫是模拟浏览器向服务器发送请求的过程,定制对象是一种反爬虫的手段
需要使用headers定制操作系统
import urllib.request
url='https://www.baidu.com'
#url组成
# https://www.baidu.com/s?wd=周杰伦
#http/https www.baidu.com 80/443 s wd = 周杰伦 #
# 协议 主机 端口号 路径 参数 锚点
# http 80
# https 443
# mysql 3306
# oracle 1521
# redis 6379
# mongodb 27017
#headers字典
headers={
'User-Agent':'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/86.0.4240.198 Safari/537.36'
}
# 因为urlopen方法中不能存储字典,所以headers不能传递进去
# 请求对象的定制
# 注意 因为参数顺序的问题,不能直接写url 和 headers 中间还有data 所以我们需要关键词传参
request=urllib.request.Request(url=url,headers=headers)
response=urllib.request.urlopen(request)
content=response.read().decode('utf8')
print(content)
# response = urllib.request.urlopen(url)
#
# content = response.read().decode('utf8')
#
# print(content)
1.get请求的quote方法(把中文转换成unicode编码)
#需求 获取https://www.baidu.com/s?wd=周杰伦的源码
#https://www.baidu.com/s?wd=%E5%91%A8%E6%9D%B0%E4%BC%A6
import urllib.request
import urllib.parse
url='https://www.baidu.com/s?wd='
#请求对象的定制是为了解决反爬的一种手段
headers={
'User-Agent':'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/86.0.4240.198 Safari/537.36'
}
#要将周杰伦三个字变成unicode编码
#我们需要依赖于urllib.parse
name=urllib.parse.quote('周杰伦')
print(name)
url=url+name
print(url)
#请求对象的定制
request=urllib.request.Request(url=url,headers=headers)
#模拟浏览器向服务器发送请求
response=urllib.request.urlopen(request)
#获取响应内容
content=response.read().decode('utf-8')
#打印数据
print(content)
2.get请求的urlencode方法
适用于多个参数的情况之下,直接定义为一个字典形式
#urlencode应用场景:多个参数的时候
#https://www.baidu.com/s?wd=周杰伦&sex=男、
import urllib.parse
import urllib.request
#
# data={
# 'wd':'周杰伦',
# 'sex':'男',
# 'location':'中国台湾省'
# }
# a=urllib.parse.urlencode(data)
# print(a)
base_url='https://www.baidu.com/s?'
data={
'wd':'周杰伦',
'sex':'男',
'location':'中国台湾省'
}
new_data=urllib.parse.urlencode(data)
url=base_url+new_data
headers={
'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/86.0.4240.198 Safari/537.36'
}
#请求对象的定制
request=urllib.request.Request(url=url,headers=headers)
#模拟浏览器向服务器发送请求
response=urllib.request.urlopen(request)
#获取网页源码的数据
content=response.read().decode('utf-8')
#打印数据
print(content)
3.post请求百度翻译
注意:post请求的参数 必须进行编码
POST的请求参数是不会拼接在url后面的,而是需要放在请求对象定制的参数中
#post请求
import urllib.request
import urllib.parse
url='https://fanyi.baidu.com/sug'
headers={
'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/86.0.4240.198 Safari/537.36'
}
data={
'kw':'spider'
}
#post请求的参数 必须进行编码
data=urllib.parse.urlencode(data).encode('utf-8')
print(data)
#POST的请求参数是不会拼接在url后面的,而是需要放在请求对象定制的参数中
#post请求的参数,必须要进行编码
request=urllib.request.Request(url=url,data=data,headers=headers)
print(request)
#模拟浏览器向服务器发送请求
response=urllib.request.urlopen(request)
#获取响应的数据
print(response)
#获取响应的数据
content=response.read().decode('utf-8')
print(content)
#字符串转换成json对象
import json
obj=json.loads(content)
print(obj)
4.ajax的get请求豆瓣电影的第一页
保存信息到文件之中一共有两种方式
1.
fp=open('douban.json','w',encoding='utf-8')
fp.write(content)
fp.close()
2.
with open('douban1.json','w',encoding='utf-8') as fp:
fp.write(content)
fp.close()
#get请求
#获取豆瓣电影的第一页的数据 并且保存起来
import urllib.request
url='https://movie.douban.com/j/chart/top_list?type=5&interval_id=100%3A90&action=&start=0&limit=20'
headers={
'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/86.0.4240.198 Safari/537.36'
}
#1.请求对象定制
request=urllib.request.Request(url=url,headers=headers)
#2.获取响应的数据
response=urllib.request.urlopen(request)
content=response.read().decode('utf-8')
print(content)
#3.数据下载到本地
#open方法默认情况使用的是gbk的编码 如果我们要想保存汉字 那么需要在open方法中指定编码格式utf-8
# encoding='utf-8'
# fp=open('douban.json','w',encoding='utf-8')
# fp.write(content)
# fp.close()
# import json
# obj=json.loads(content)
# print(obj)
with open('douban1.json','w',encoding='utf-8') as fp:
fp.write(content)
fp.close()
5.Ajax的get请求豆瓣电影的前10页
需要用到函数把其分段进行循环输出
import urllib.request
import urllib.parse
#https://movie.douban.com/j/chart/top_list?type=5&interval_id=100%3A90&action=&start=0&limit=20
#https://movie.douban.com/j/chart/top_list?type=5&interval_id=100%3A90&action=&start=20&limit=20
#https://movie.douban.com/j/chart/top_list?type=5&interval_id=100%3A90&action=&start=40&limit=20
#page 1 2 3 4
#start 0 20 40 60
#start (page-1)*20
#下载豆瓣电影前10页的数据
#1.请求对象的定制
#2.获取响应的数据
#3.下载数据
def create_request(page):
base_url='https://movie.douban.com/j/chart/top_list?type=5&interval_id=100%3A90&action=&'
data={
'start':(page-1)*20,
'limit':20
}
data=urllib.parse.urlencode(data)
url=base_url+data
print(url)
headers = {
'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/86.0.4240.198 Safari/537.36'
}
request=urllib.request.Request(url=url,headers=headers)
return request
def get_content(request):
response=urllib.request.urlopen(request)
content=response.read().decode('utf-8')
return content
def down_load(page,content):
with open('douban_'+str(page)+'.json','w',encoding='utf-8') as fp:
fp.write(content)
#程序的入口
if __name__ == '__main__':
start_page=int(input('请输入起始页码'))
end_page=int(input('请输入结束页码'))
for page in range(start_page,end_page+1):
# 每一页都有自己的请求对象的定制
request=create_request(page)
# 获取响应的数据
content=get_content(request)
# 下载
down_load(page,content)
6.ajax的post请求肯德基官网
import urllib.request
import urllib.parse
#base_url='http://www.kfc.com.cn/kfccda/ashx/GetStoreList.ashx?op=cname'
def create_request(page):
base_url = 'http://www.kfc.com.cn/kfccda/ashx/GetStoreList.ashx?op=cname'
data={
'cname':'北京',
'pid':'',
'pageIndex':page,
'pageSize':10
}
data=urllib.parse.urlencode(data).encode('utf-8')
headers = {
'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/86.0.4240.198 Safari/537.36'
}
request=urllib.request.Request(url=base_url,headers=headers,data=data)
return request
def get_content(request):
response=urllib.request.urlopen(request)
content=response.read().decode('utf-8')
return content
def down_load(page,content):
fp=open('kfc_'+str(page)+'.json','w',encoding='utf-8')
fp.write(content)
fp.close()
if __name__ == '__main__':
start_page=int(input('请输入起始页码'))
end_page = int(input('请输入结束页码'))
for page in range(start_page,end_page+1):
# 请求对象的定制
request=create_request(page)
# 获取网页源码
content=get_content(request)
# 下载
down_load(page,content)
7.微博的cookie登录
#适用场景:数据采集的时候,需要绕过登录,然后进入到某个页面
import urllib.request
url='https://weibo.com/u/5494282906'
headers={
# 'authority': 'weibo.com',
# 'method': 'GET',
# 'path': '/ajax/profile/info?uid=5494282906',
# 'scheme': 'https',
'accept': 'application/json, text/plain, */*',
# 'accept-encoding': 'gzip, deflate, br',
'accept-language': 'zh-CN,zh;q=0.9',
'client-version': '2.34.75',
# cookie中携带着你的登录信息 如果有登陆之后的cookie 那么我们就可以携带者cookie进入到任何页面
'cookie': 'SINAGLOBAL=4321438772735.1265.1638876314958; UOR=,,www.huya.com; XSRF-TOKEN=0Y1gSmTH7wyvdhpyilfV_vlf; PC_TOKEN=10a79267b9; login_sid_t=356705c36e6e3ef551138a832110c242; cross_origin_proto=SSL; WBStorage=4d96c54e|undefined; _s_tentry=weibo.com; Apache=2620855400086.0684.1659428891597; ULV=1659428891603:5:1:1:2620855400086.0684.1659428891597:1658372773115; wb_view_log=1920*10801; SUB=_2A25P7JBkDeRhGeNK4lYT-CzFyzqIHXVsm4asrDV8PUNbmtANLVfxkW9NSS8zowa0jAsEWFtjMyrrJhhbJb1BXURy; SUBP=0033WrSXqPxfM725Ws9jqgMF55529P9D9WhSQTOOaS3AEmM3FHDZyNqZ5JpX5KzhUgL.Fo-X1KBE1hz4ehq2dJLoIE-LxKnLBoqL1h-LxKMLB.2LBKMLxK.L1hML1K2LxKML12eLBoxu; ALF=1690964916; SSOLoginState=1659428917; WBPSESS=U2WFjk9l_oENTuN-ANFxmzGiwhSrHzYTavgzgmNaP5OU_qgTbyEYEFAvw7wHHNGa2WHU1KDVGkSTJwj61IcxVEYa22hAhm0IFE0Ig-zzZSCZhGbs0dG4VRbdhnYzcsjhdnx-e4jptHJ2HLHmIs7HIQ==',
# referer 判断当前路径是不是由上一个路径进来的 一般情况下是做图片防盗链
'referer': 'https://weibo.com/u/5494282906',
'sec-fetch-dest': 'empty',
'sec-fetch-mode': 'cors',
'sec-fetch-site': 'same-origin',
'server-version': 'v2022.08.01.2',
'traceparent': '00-2841b7aa70142fce9b3da2c5022e1be5-4a79deee3f4f0e4e-00',
'user-agent': 'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/86.0.4240.198 Safari/537.36 QIHU 360SE',
'x-requested-with': 'XMLHttpRequest',
'x-xsrf-token': '0Y1gSmTH7wyvdhpyilfV_vlf',
}
#请求对象的定制
request=urllib.request.Request(url=url,headers=headers)
#模拟浏览器向服务器发送请求
response=urllib.request.urlopen(request)
#获取相应数据
content=response.read().decode('utf-8')
#将数据存储到本地
fp=open('weibo.html','w',encoding='utf-8')
fp.write(content)
fp.close()
8.handle处理器的基本使用
#需求 需要handler来访问百度 获取网页源码
import urllib.request
url = 'https://baidu.com'
headers = {
'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/86.0.4240.198 Safari/537.36'
}
request=urllib.request.Request(url=url,headers=headers)
#handler build_opener open
# 1.获取hanlder对象
handler=urllib.request.HTTPHandler()
# 2.获取opener对象
opener=urllib.request.build_opener(handler)
# 3.调用Open方法
response=opener.open(request)
content=response.read().decode('utf-8')
print(content)
9.代理服务器
1.代理的常用功能
1.突破自身ip访问限制,访问国外站点
2.访问一些单位或团体内部资源
扩展:某大学FTP(前提是该代理地址在该资源的允许访问范围之内),使用教育网内地址免费代理服务器,就可以用于对教育网开房的各类FTP下载上传,以及各类资料查询共享等服务
3.提高访问速度
扩展:通常代理服务器都设置一个较大的硬盘缓冲区,当有外界的信息通过时,同时也将其保存到缓冲区中,当其他用户再访问相同的信息时,则直接由缓冲区取出信息,传给用户,以提高访问速度
4.隐藏真实ip
扩展:上王者也可以通过这种方法隐藏自己的ip,以免遭受攻击
2.代码配置代理
创建Reuqest对象
创建ProxyHandler对象
用handler对象创建opener对象
使用opener.open函数发送请求
import urllib.request
url='http://www.baidu.com/s?wd=ip'
headers = {
'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/86.0.4240.198 Safari/537.36',
}
#请求对象定制
request=urllib.request.Request(url=url,headers=headers)
#模拟浏览器访问服务器
#response=urllib.request.urlopen(request)
proxies={
'http':'221.4.241.198:9091'
}
#handler build_opener open
handler=urllib.request.ProxyHandler(proxies=proxies)
opener=urllib.request.build_opener(handler)
response=opener.open(request)
#获得相应信息
content=response.read().decode('utf-8')
#保存
fp=open('daili.html','w',encoding='utf-8')
fp.write(content)
fp.close()