首页 » Web前端 » phpheader跳页技巧_基于社交收集爬虫分析人物兴趣属性三

phpheader跳页技巧_基于社交收集爬虫分析人物兴趣属性三

访客 2024-12-04 0

扫一扫用手机浏览

文章目录 [+]

本文所有代码都已经发布在github项目主页上

https://github.com/smityliu/spider

phpheader跳页技巧_基于社交收集爬虫分析人物兴趣属性三

微博仿照登录、推特仿照登录

久等了各位伙伴们,本篇文章是我们社交网络人物画像的第三篇,也是我们爬虫最技能含量最为丰富的一篇,之前的两篇文章基于社交网络爬虫剖析人物兴趣属性(一);基于社交网络爬虫剖析人物兴趣属性(二)揭橥了往后,有师傅问过我为什么不做一下仿照登录,会比较好,然后也给了我很多建议,比如如何做数据对齐的建议,看来实在人物画像真的很多师傅有履历,现在大公司也做大数据剖析的事情。

phpheader跳页技巧_基于社交收集爬虫分析人物兴趣属性三
(图片来自网络侵删)

我没有直接公开仿照登录的研究过程是由于之前爬虫违规利用的问题闹得沸沸扬扬,以是我不太想在公开平台谈论海内的社交网络,但是后来瞥见大部分的论坛实在都有公开了新浪微博或者知乎一类的仿照登录,并且我也讯问了很多白帽子的同寅,知道了实在正常利用仿照登录是许可的。
下面就来进入本日大家都很想看的主题——新浪微博仿照登录和推特仿照登录。

为什么须要这个呢,由于我们碰着了两个问题:

1. 我们之前只选取了一个社交网络,数据有时性太大了,得选取两个——微博和推特

2. 两个网路哦就必须要做数据对齐,如何担保你做数据领悟的两个用户是同一个人,必须得找到干系得信息

在数据对齐的时候要搜索足够多的用户干系信息,个中某用户关注的职员便是很主要的一块,但是我们如果不上岸是看不到他们的关注的:

递归爬取模型:

在讲仿照登录之前我们必须要做一个事情,便是明确登录后我们要干嘛——爬取用户的关注。

那么这里就会有一个问题:爬一个够吗,肯定不足,我们须要爬好几层。
什么叫做好几层呢?便是递归爬取,递归之前我们须要确定“种子”和“层数”:

比如,确定种子为娱乐圈的10个人

孙燕姿,郭德纲,周润发,朱茵,宋丹丹,冯小刚,科比,乔丹,刘翔,泰勒斯威夫特,贾斯汀比伯,甄子丹,成龙,张纪中

确定情由,包含了导演,影视圈演员,歌手,艺术家,国外歌手,体育明星,个中歌手包含老一辈和新一代,并且是个种子里面都有相互干联的人

每个种子都爬取两层关注,便是他自己这一层,加上他关注的人的关注,基本可以做到覆盖所有的娱乐圈,微博两层拓展后的总数据量有1万多人,推特少一些,但是也有大概3,4千人旁边

这个地方有三个单位:

1. 每层2. 每层的个人3. 每个人的关注凑集

递归的模型是

按照优先级"每个人>每个人凑集>每一层>递归",便是先第1层第一个:[],然后获取这一个的凑集,然后第1层第二个:[],然后回去这一个的凑集...... 这一层的每一个弄完往后,进行递归,然后再找第2层的第一个、第二个、第三个,以此类推。

情由:任何一个顺序颠倒都会增加运算量或者编程难度

1. 如果先弄一层再取每一个人的凑集,那么会多一次for循环遍历。

2. 如果每一个取完两层再换下一个,那么会多n的2次方运算,大家可以试试。

递归开始:

举个例子,冯小刚关注了吴京,吴京关注了胡歌,胡歌又关注了吴君如,吴君如又有很多喷鼻香港明星的微博,导演这一层就可以拓展到所有演员

在演员中,只要有人关注了歌手,比如郑凯关注了黎明,那么黎明里的关注又会有一个上海合唱团他曾经辅导过的团队,这个团队又会关注著名主持人何炅,何炅又关注了很多非演员歌手得明星比如岳云鹏,又会将影视圈演艺圈拓宽到综艺圈和相声界,然后在这些人中有一个关键节点金星老师,她关注了刘翔,从而拓展到了体育界,再拓展到国外。

之后的两个仿照登录,我们就直接把这个算法模型带入到爬虫中。

微博仿照登录

首先,明确一点——关于爬虫,“只要能够通过浏览器看到的,你肯定都能爬下来,只是难度不同”:

最难的爬虫:带验证码,目前识别验证码的库和爬虫都已经达到商业级别,确实很不好做或者每次爬取的成功几率都很小。

最大略的爬虫:没有任何验证机制,post传入用户名和密码到表单就直接可以获取cookie了。

我们先来看新浪微博:

可惜有验证码,那这个肯定事情量很大了,但是,上天还是照顾研讨的人,让我创造了一个绕过的地方:微博手机端

由于我自己也用微博,以是在手机上也安装了微博的app,用浏览器打开后,创造他的域名是这个:https://weibo.cn/pub/

很惊喜的地方在于

根本不须要验证码有木有!

以是很大略了,直接Burpsuite截取包:

创造有一下几个字段(username,password,cookie已经被我删除):

headers={ 'Host': 'passport.weibo.cn', 'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:71.0) Gecko/20100101 Firefox/71.0', 'Accept': '/', 'Accept-Language': 'zh-CN,zh;q=0.8,zh-TW;q=0.7,zh-HK;q=0.5,en-US;q=0.3,en;q=0.2', 'Content-Type': 'application/x-www-form-urlencoded', 'Origin': 'https://passport.weibo.cn', 'Connection': 'close', 'Referer': 'https://passport.weibo.cn/signin/login?entry=mweibo&r=https%3A%2F%2Fweibo.cn%2F&backTitle=%CE%A2%B2%A9&vt=', 'Cookie':'你的cookie' } data={ 'username': '你的用户名', 'password': '你的密码', 'savestate': '1', 'r': '', 'ec': '0', 'pagerefer': 'http://weibo.cn/', 'entry': 'mweibo', 'wentry': '', 'loginfrom': '', 'client_id': '', 'code': '', 'qq': '', 'mainpageflag': '1', 'hff': '', 'hfp': '', }

如果登录失落败,则会显示以下:

如果登录成功则retcode为“20000000”,截取报文的效果如下图

在github上的完全代码:https://github.com/smityliu/spider/blob/master/weibo_login.py

也便是须要你们填写username,password,cookie三个字段就可以了

以是,上岸部分的代码就用requests中的session.post完成,检测2000000在不在相应报文里面就好了:

login=session.post(url=url,headers=headers,data=data) if("20000000" not in login.text): print("上岸失落败") exit() login.encoding='utf-8'

在微博的手机端里,用户有三个属性——id,用户昵称,用户名

用户关注列表是用

https://weibo.cn/+id+/follow

这样的形式构成的,id和用户的唯一用户名不同,他不会放在展示页面,必须自己提取。
而这个id可以这么提取:

在爬取关注列表后,我们创造每个关注职员返回的数组都含有主页和用户昵称:

<td valign="top"><ahref="https://weibo.cn/u/2530520950">风吹铃铛响叮叮</a>

然后访问这个主页会创造,在关注连接的地方有href连接,包含了id和关注页面的连接:

<a href="/2530520950/follow">关注[583]</a>

以是我们的递归便是:

1. 爬取用户的关注列表

2. 从中提取每个用户的主页和昵称

3. 在主页中正则提取关注连接,获取id

4. 将所有id整合为list,作为下一次递归的输入

接下来我们导入递归算法,这里有几个坑,比如微博有反爬虫机制,如果你的要求速度过快,纵然登录之后,他也会将你302重定向到security.api去,并且让你输入短信验证码,代码运行后是如下情形而不是登录失落败。

涌现这样的情形不要怕,肯定是微博已经将你加入限定了,限定了你的免验证登录。
办理办法:

1. 先去weibo.cn试试登录看,有没有要你验证身份,如果有,重新申请一个账户吧,这个是不会取消的重新,申请一个账户就可以免去检讨。

2. 重新申请一个账户后,每一个账户只管即便在固定ip下用同一种办法登录,也便是说,用脚本登录后,只管即便不要太频繁的用浏览器登录了,会检测的。

3. 在你出问题的要求代码后面写入sleep几秒,这样就比较稳定

以是我调度过后的代码很稳定,每一次要求都会sleep一段韶光,基本爬下来几百个用户不成问题,效果如下

将爬取结果写入文件效果如下:

稳定递归+写入文件代码如下,完全代码已经放在github上

https://github.com/smityliu/spider/blob/master/weibo_login.py:

def follow_spider(id_all,turn): #掌握迭代次数 if(turn == 2): print('\n'+"已经达到须要爬取的层数,准备退出......") exit() else: #最外层的for,是用来循环这一层函数中id_all的值 print('第'+str(turn)+'层开始:'+'\n'+'该层须要爬取的id有:') print(id_all) uid_all=[] for id in id_all: people=0 time.sleep(5) #登录往后利用新的headers headers_logined={'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:71.0) Gecko/20100101 Firefox/71.0'} #先标记名字id url_for_name='https://weibo.cn/'+id try: l=session.get(url=url_for_name,headers=headers_logined,timeout=3) name=re.findall(r'<title>(.?)的微博</title>',l.text) print('\n'+'开始爬取'+id+'||'+name[0]+'的所有关注\n') except: continue follow_url= 'https://weibo.cn/'+str(id)+'/follow' login=session.get(url=follow_url,headers=headers_logined,timeout=3) pages = re.findall(r'value="跳页" /> 1\/(.?)页',login.text) #print(pages) if len(pages)==0: print('\n'+"只有一页,以下是"+id+'||'+name[0]+'的所有关注') page_all=['0'] else: page_all=str(pages[0]) follow_all=[] uid_part=[] print(page_all) if(page_all[0]=="0"): follow_url = 'https://weibo.cn/'+str(id)+'/follow' login=session.get(url=follow_url,headers=headers_logined,timeout=3) follow_part=re.findall(r'<td valign="top"><a.?href="(.?)">(.?)</a>',login.text) follow_all = follow_all+follow_part else: #循环取每一页的关注和他的主页,但是这里取不到id,以是还得连续根据主页取 for page in range(int(page_all)): page = page+1 follow_url = 'https://weibo.cn/'+str(id)+'/follow?page=' + str(page) login=session.get(url=follow_url,headers=headers_logined,timeout=3) #匹配出来结果为关注的用户名昵称,是个二重数组,list里面再有一个list,follow_part[1][0]取主页url,follower[1][1]来取用户名 follow_part=re.findall(r'<td valign="top"><a.?href="(.?)">(.?)</a>',login.text) follow_all = follow_all+follow_part time.sleep(3) #当关注数量大于150个的时候,跳过不打算 #follow_all为所有关注及其对应的主页 print(follow_all) #根据主页取每一个关注的id,凑成uid_all name_list=[] for s in range(len(follow_all)): if("微博" in follow_all[s][1]): continue follower=session.get(follow_all[s][0],headers=headers_logined,timeout=3) uid = re.findall(r'私信</a> <a href="/(.?)/info">资料</a>',follower.text) print(str(s) +' '+ follow_all[s][1] + ': ') print(uid) #这是某一个的总凑集 uid_part = uid_part + uid name_list.append(follow_all[s][1]) #people=people+1 #if(people>50): # print("已经爬取前50个关注") # break time.sleep(1.5) print('\n'+'这是'+id+'__'+name[0]+'的所有关注') #写入每个文件的一定假如用户名,才好做数据对齐 print(name_list) file_name=name[0]+'.txt' with open('./weibo/'+file_name,'w',encoding="utf-8") as f: f.write(str(name_list)) #for one in uid_part: # url_one='https://weibo.cn/'+one # l=session.get(url=url_one,headers=headers_logined) # name_one=re.findall(r'<title>(.?)的微博</title>',l.text) # name_list = name_list+name_one print('\n该用户的关注名单已经写入文件\n') #这层的某一个算完往后加入这一层的总凑集) uid_all=uid_part+uid_all #print('第'+str(turn)+'层得到的结果:') #print(uid_all) #最外层循环结束 print('\n'+'第'+str(turn)+'层结束:') turn = turn +1 follow_spider(uid_all,turn)

推特仿照登录

推特的仿照登录是这个项目里最难的,网络上的方法大多数都弗成,都是好几年前的,推特早就不用那个构造了。

我们来剖析一下推特,创造没有任何验证码,有点高兴:

但是我们直接截取登录报文,考试测验登录却创造他有好多随机的字段,特殊是这个authenticity_token,你直接复制一个现成切实其实定是弗成的,仿照登录后一定是跳转302到login界面,见告你登录失落败。
而且他登录的url是sessions,并不是login.html,推特的前端验证做的还是挺风雅的。

但是也有漏洞,我们创造直接访问

https://twitter.com/login

这个页面,直接就有authenticity_token

以是实在他只是一个访问前端就可以获取的随机值,因此我们的仿照登录如下:

完全代码在(https://github.com/smityliu/spider/blob/master/weibo_login.py)

还没有结束,推特的仿照登录成功不是重点,他难就难在,你想查看用户的信息,后台是调用各种api来返回给你json数据

你登录了,肯定想:欸我直接爬

https://twitter.com/Stefsunyanzi/following

它不喷鼻香么

不好意思,还真弗成,你直接爬取following页面,里面会调用各种api接口,你只爬下来了一个following页面都是代码,一找api,都是404,直接爬会涌现这个页面

我们攻破这个api,真的是一个很麻烦,很繁琐的过程,一堆json让你看,你得一个个相应包看过去,终于看到了关注职员的json包:

如果你想侥幸,直接复制当前的所有header和data进行requests要求,那么它一定返回:

{"errors":[{"code":215,"message":"BadAuthentication data."}]}

由于你的要求办法不对。

我们看一下它的要求包:

Request URL: https://api.twitter.com/1.1/friends/list.json?include_profile_interstitial_type=1&include_blocking=1&include_blocked_by=1&include_followed_by=1&include_want_retweets=1&include_mute_edge=1&include_can_dm=1&include_can_media_tag=1&skip_status=1&cursor=-1&user_id=83570815&count=20Request Method: GETStatus Code: 200 Remote Address: 127.0.0.1:10809Referrer Policy: no-referrer-when-downgradeauthorization: Bearer …….Origin: https://twitter.comReferer: https://twitter.com/Stefsunyanzi/followingSec-Fetch-Mode: corsUser-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/76.0.3809.87 Safari/537.36x-csrf-token: 081e09c5b2c1b13627ee8a9309de6131x-twitter-active-user: yesx-twitter-auth-type: OAuth2Sessionx-twitter-client-language: eninclude_profile_interstitial_type: 1include_blocking: 1include_blocked_by: 1include_followed_by: 1include_want_retweets: 1include_mute_edge: 1include_can_dm: 1include_can_media_tag: 1skip_status: 1cursor: -1user_id: 83570815count: 20

这看一下傻眼了,利害一起来:

你说这个好登录吧,它也很好登录,由于authorization(我自己的删除了)这个东西便是储存你登录信息的字段,你只要有了这个字段,随便调用api了。

你说这个难登录吧,它贼难,各种随机字段,x-csrf-token这个字段真的是很劝退了,你如果你忽略这个字段,它一定提示你,this requests need matchcsrf-token这个报错,便是见告你你得有这个token,我们曾经为了这个问题,真的险些快放弃了推特登录。

但是真的上天眷顾不放弃的人,有时一天晚上随便看字段创造个不得了的东西:

cookie: _ga=; tfw_exp=0; kdt=w; remember_checked_on=1; csrf_same_site_set=1; csrf_same_site=1; des_opt_in=Y; fontsLoaded=true; ct0=081e09c5b2c1b13627ee8a9309de6131; _gid=; lang=en; _sl=1; personalization_id="v"; guest_id=; ads_prefs="HBERAAA="; _twitter_sess=; auth_token=; rweb_optin=side_no_out; twid=u%3D1203136912770224128; _gat=1

这cookie里的ct0字段不便是我们要找的x-csrf-token吗,但是还有一个问题便是,这个东西到底是做事端给的,还是自己客户端随机天生的,我们实验了一下:

每次的x-csrf-token都不一样,但是长度肯定是一样的

直接修正x-csrf-token为97e791a574a3a81468622aefcee61068,然后要求,他返回的结果写入文件后便是:

要求返回的是我们须要的json内容,而不是405要求失落败,里面包含了用户的id,用户的昵称和用户的唯一名字。

这个解释csrf-token在推特的登录机制中是由客户端天生并且给做事真个,这个就很好做了啊,我随便利用一个曾经登录获取到的csrftoken然后修正cookie里的ct0字段为这个值,就可以直接登录了。

怎么看用户的id呢,

不雅观察提取用户关注的url,创造是和用户id有关的:

https://api.twitter.com/1.1/friends/list.json?include_profile_interstitial_type=1&include_blocking=1&include_blocked_by=1&include_followed_by=1&include_want_retweets=1&include_mute_edge=1&include_can_dm=1&include_can_media_tag=1&skip_status=1&cursor=-1&user_id='+str(ids)+'&count=100'

以是我们的递归爬取如下:

利用种子的id,爬取种子的关注列表正则匹配关注职员的id和用户名将所有id合并为下一次递归的凑集

以是登录之后,我们只要循环取json里的id,并且将id作为下一次递归的输入,就可以利用用户id直接递归爬取了,以是我们的代码如下:

def spider_follower(id_all,name_all,turn): print("这是第"+str(turn)+"层:") print(id_all) print(name_all) if(turn == 3): print("达到层数,退出") exit() headers_json={ 'authorization': 'Bearer …..', 'content-type': 'application/x-www-form-urlencoded', 'Origin': 'https://twitter.com', 'Sec-Fetch-Mode': 'cors', 'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/76.0.3809.87 Safari/537.36', #建议每次用脚本之前,都去浏览器再重新更新一下cookie,以防过期,获取过程很大略,直接看发包就可以了,然后全体脱下来。
'Cookie':'_ga= , 'x-csrf-token':'97e791a574a3a81468622aefcee61068'} position=0 id_next_all=[] follower_name_all=[] for ids in id_all: url='https://api.twitter.com/1.1/friends/list.json?include_profile_interstitial_type=1&include_blocking=1&include_blocked_by=1&include_followed_by=1&include_want_retweets=1&include_mute_edge=1&include_can_dm=1&include_can_media_tag=1&skip_status=1&cursor=-1&user_id='+str(ids)+'&count=100' follower = session.get(url=url,headers=headers_json,proxies=proxies) follower_json=json.loads(follower.text) #print(follower_json) follower_name=[] id_next=[] #这个follower是json格式了已经,follower_json["users"]还是一个list for follower in follower_json["users"]: #print("screen_name: "+follower["screen_name"]) id_next.append(follower["id_str"]) follower_name.append(follower["name"]) print('\n') print(ids) str(name_all[position]).replace(' ','_').replace('?','_').replace('.','_').replace('/','_').replace('\\','_').replace('"','_').replace('<','_').replace('>','_').replace('|','_').replace('\'','_') filename=str(name_all[position])+'.txt' print(filename) print('\n') try: with open('./twitter/'+filename,'w',encoding='utf-8') as f: f.write(str(follower_name)) except: pass position=position+1 id_next_all=id_next_all+id_next follower_name_all = follower_name_all + follower_name turn = turn +1 print(id_next_all) print(follower_name_all) spider_follower(id_next_all,follower_name_all,turn)

完全代码在

https://github.com/smityliu/spider/blob/master/twitter_login_test.py

各位利用的时候只要截取一下流量包,输入你的用户名密码,和authorization,cookie,然后将cookie里的ct0字段填入csrftoken(可以循环利用,不检讨),就可以愉快的一贯爬取了。
实在用不来可以联系我。

效果如图:

左边是推特,右边是微博

写入文件后

有趣的是我这里创造authorization实在是来自登录后的主页js文件

如果你们有兴趣可以再把爬虫智能化一点。
合天网安实验室的一个干系实验:通过该实验,基于之前所学的爬虫知识,理解一些常用的百度的高等搜索语法,并且自己编写一个属于自己的url采集器。
复制链接做实验啦:http://www.hetianlab.com/expc.do?ec=ECID2a0a-fa3e-461c-a570-8fe95bbedd46

下一篇预报

我们拿到了所有的数据,将开始我们的扫尾事情:

1. 做数据对齐,两个网络如何担保你能够确定领悟数据得两个用户是同一个人,必须得找到干系得信息。
我们采纳的是比拟关注人物的相似度,但是第一个问题在于,海内明星在推特上大部分都是英文名,以是还得做一步事情,便是百度引擎搜索推特关注的英文名,并且提取第一页词条涌现频率最高的词语作为这个用户的中文代号,比如JJ_LIN,打消停用词后,百度词条首页最多涌现的的是林俊杰,那么就将林俊杰更换推特里的JJ_LIN

2. 将微博的每一个用户的关注以用户名命名存放在weibo目录下,推特也类似,存放在twitter目录下,然后利用余弦定理相似度比较法,打算两个文件夹中每个分词后,两两比较得出的词语之间的间隔,用间隔关系来判断相似程度大小

3. 同时加上关注职员的社会属性,社会属性在第一篇爬虫里面就有提到,可以直接爬取到对运用户的微博里面的社会认证资料,那个是完备精确的

4. 末了,领悟微博帖子和推特的推文,用第二篇LDA重新演习,得到兴趣属性

声明:笔者初衷用于分享与遍及网络知识,若读者因此作出任何危害网络安全行为后果自大,与合天智汇及原作者无关!

标签:

相关文章

介绍百度码,技术革新背后的智慧之光

随着科技的飞速发展,互联网技术已经成为我们生活中不可或缺的一部分。而在这个信息爆炸的时代,如何快速、准确地获取信息,成为了人们关注...

Web前端 2025-01-03 阅读4 评论0

介绍皮箱密码,开启神秘之门的钥匙

皮箱,作为日常生活中常见的收纳工具,承载着我们的珍贵物品。面对紧闭的皮箱,许多人却束手无策。如何才能轻松打开皮箱呢?本文将为您揭秘...

Web前端 2025-01-03 阅读4 评论0

介绍盗号器,网络安全的隐忧与应对步骤

随着互联网的快速发展,网络安全问题日益突出。盗号器作为一种非法工具,对网民的个人信息安全构成了严重威胁。本文将深入剖析盗号器的原理...

Web前端 2025-01-03 阅读2 评论0