基本流程:
1:获取目标URL资源
2:解析网站,获取需要的数据
3:以适当的方式存储数据
requests库是一个简洁且简单地处理HTTP请求的第三方库,优点是更接近正常URL的访问过程。
请求页面的函数包括get()和post(),返回一个response对象。
| 函数 | 作用 |
| get(url,header,timeout) | 对应于HTTP的GET函数 ,需要在header里面存入本机的user-agent和cookie,可以使用字典的方式存储,timeout设定每次请求超时的时间(如果不设置的话如果请求目标URL无响应的话,程序可能挂起) |
| post(url,header,timeout,data={}) | 对应于HTTP的POST函数,data存放post需要提交的数据 |
注意:
1.获取本机的user-agent和cookie的方式是打开目标网页,f12打开控制台,选择network然后刷新页面,点击刷新后出现的第一行,最后一个参数是user-agent,往上翻一点是cookie。需要注意的是,一台机器的user-agent好像和ip有关,所以一般不会更换,而cookie是可能变化的,如发现程序无法正常四合院,可更换新的cookie。
2.GET方式通过url提交数据,且限制提交的数据不超过1024bytes,post通过json格式传输数据,没有限制,一般用GET即可。
| Response的属性 | 描述 |
| status_code | HTTP请求的返回状态,200表示连接成功,404表示拒绝,302表示重定向。 |
| text | HTTP响应内容的字符串形式,即页面内容 |
| encoding | HTTP响应内容的编码方式(有时候的错误是来自编码方式的问题,现在主流的编码方式为utf-8,但是有些资源的编码可能是gbk等,如果报了一些类型错误可能因为编码方式 |
| content | HTTP响应内容的二进制形式,如果是要获取图片等数据通过解码content,解码方式跟你要解码的内容有关 |
| requests可能产生的异常 | 描述 |
| ConnectionError | 遇到网络问题,如DNS查询失败,拒绝连接等 |
| HTTPError | 无效的HTTP响应 |
| TimeOut | 请求url超时 |
| TooManyRedirects | TooManyRedirects,大概是页面重定向过多吧 |
本次实例是爬取某条微博下的评论,爬取的网站是微博移动网页版,因为页面越简单,对于我们爬虫来说越简单。
微博移动网页版(.cn)
下面是实际请求页面和查看response对象的text
import requests
wid="KDW8lBr7u" # 张艺兴
headers={'user-agent':'你的user-agent','cookie':'你的cookie'}# ''内分别替换为你的user-agent和cookie
res = requests.get('https://weibo.cn/comment/{}'.format(wid), headers=headers, verify=False)
print(res.text)
其中,wid是目标微博的id,获取方式为打开该微博,在地址栏里找到如下部分。
微博id:KDW8lBr7u
注意:这里是微博web版(.com)
显示的结果(部分)为:
其原始微博(.cn版)为
此时其实已经可以单单通过正则表达式解析response.text来获取需要的评论,不过使用BS4库封装的功能会更简单。
使用bs4解析html:
import requests
from bs4 import BeautifulSoup
import re
import time
headers = {
'user-agent': 'Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/95.0.4638.54 Safari/537.36',
'cookie': 'SUB=_2A25MigQcDeRhGeNL41MZ8i3IzDmIHXVv_nLUrDV8PUJbmtAKLRmskW9NSMoBqAOXZWA0Ote9nf_TWK4mKAY4Z6zc; SUBP=0033WrSXqPxfM725Ws9jqgMF55529P9D9WF-34ls0cECS2oiChgRG5xq5NHD95QfSKnp1hz0ShMfWs4Dqc_xi--ciKyWi-8Fi--NiKL2iKn7i--NiKyFi-ihi--NiKLWi-88i--NiKLWiKnXi--Ni-i8iKyWi--NiKnRi-zpi--fi-i8i-88i--fiKy2iKLW; SSOLoginState=1636725836; _s_tentry=weibo.cn; UOR=weibo.cn,s.weibo.com,weibo.cn; Apache=3178612076774.905.1636726193838; SINAGLOBAL=3178612076774.905.1636726193838; ULV=1636726193847:1:1:1:3178612076774.905.1636726193838:; XSRF-TOKEN=dXDaC-O-NZAjcirjW5rMUe9S; WBPSESS=yYvPu1D9EtlrXECbMbIIiyj3dP4WTy7m9Mmnz1oJa439wDhdmpsQOVlguNa5p_hkF1oUUlMl4c4TfmeTMWpH6hf49_vMgVY8fS8qNJZA9ioCM6iP7u9lif5OBuR0qgWnFAuYw90NOKZ5QtCCwXPFXw=='} # ''内分别替换为你的user-agent和cookie
text_comments_list = [] # list of comments
text_name_list = [] # list of names
count1 = 0 # name
count2 = 0 # comment
res = requests.get('https://weibo.cn/comment/KDW8lBr7u?rl=1&page=9', headers=headers, verify=False)
soup = BeautifulSoup(res.text, 'lxml')
print(soup)
name_list = soup.find_all('a', {'href': re.compile(r'/u/d.*')})
div_list = soup.find_all('span', class_='ctt')
for item in name_list:
count1 += 1
content = str(count1) + item.text
text_name_list.append(content)
print(content)
for item in div_list:
count2 += 1
content2 = str(count2) + item.text
text_comments_list.append(content2)
print(content2)
print("用户数:", len(text_name_list))
print("用户评论:", len(text_comments_list))
print("//")
其中,前1-10为用户id,对应后1-10为对应的评论列表。
最后得到的数据存储方式看自己需要,可以是excel,数据库,csv甚至是txt,然后按对应的方式读取即可。如果没什么要求的话建议以excel的方式,方便管理的同时也足够简单。
读取excel的方式可以用xlwt和xlrd的第三方模块,同时需要使用xlutils连接两者。具体请参考这篇文章
除了通过requests库和bs4库的组合使用,微博平台本身提供了API(微博开放平台)。微博开放平台中提供了一系列的接口,提供了丰富的功能,图只列举部分接口,具体请移步微博开放平台-文档-微博API。
首先,使用微博API需要SDKsinaweibopy3,使用时将sinaweibopy3.py文件放到工程文件的第一级,然后import sinaweibopy3即可。具体用法看openAPI的说明和案例,获得的result结构是json,所以不需要自己写复杂的解析函数。
一开始的时候尝试使用openAPI,实现了一些功能,但是与目标差距较大,而且不太理解参数中微博ID指的是什么,一开始以为是用户的用户名或者账号id,后来才知道是每条微博的自己的id。
def public_timeline(self):
'''
get new public weibo,the parameters followed can be used in _http_get in this method
access_token : (string) the token you got after OAuth
count : (int) the record items in one single page,default 50 items
page : (int) the page number,default one page
base_app : (int) whether get data in current app or not,0 is not(all data),1 is yes(current app),default 0
'''
result = _http_get('%s'% (self.api_url) + 'statuses/public_timeline.json',
access_token=self.access_token,
count=50,
page=1,
base_app=0,
)
return result
上面的代码是sinaweibopy3.py里的一个实例,每个具体的接口参数和json格式都有所不同,使用时请参数使用手册openAPI中对应接口的参数列表和实例以及博客-调用微博API获取微博内容。
参考:https://blog.csdn.net/Owen_goodman/article/details/121297589
注:本文用于学术研究,如有侵权,请联删。



