Scrapy实现模拟登录的示例代码


Posted in Python onFebruary 21, 2021

为什么要模拟登录

有些网站是需要登录之后才能访问的,即便是同一个网站,在用户登录前后页面所展示的内容也可能会大不相同,例如,未登录时访问Github首页将会是以下的注册页面:

Scrapy实现模拟登录的示例代码

然而,登录后访问Github首页将包含如下页面内容:

Scrapy实现模拟登录的示例代码

如果我们要爬取的是一些需要登录之后才能访问的页面数据就需要模拟登录了。通常我们都是利用的 Cookies 来实现模拟登录,在Scrapy中,模拟登陆网站一般有如下两种实现方式:

           (1) 请求时携带Cookies

           (2) 发送Post请求获取Cookies

请求时携带Cookies

对于一些Cookies过期时间很长的不规范网站,如果我们能够在Cookies过期之前爬取到所有我们想要的数据,可以考虑在请求时直接将Cookies信息带上来模拟用户登录。

以下是模拟登录Github的示例代码:

# -*- coding: utf-8 -*-
import scrapy
import re
 
class TmallLoginSpider(scrapy.Spider):
  name = 'github_login3'
  allowed_domains = ['github.com']
  start_urls = ['https://github.com/']
 
  def start_requests(self): # 请求时携带Cookies
    cookies = '_ga=GA1.2.363045452.1554860671; tz=Asia%2FShanghai; _octo=GH1.1.1405577398.1554860677; _device_id=ee3ff12512668a1f9dc6fb33e388ea20; ignored_unsupported_browser_notice=false; has_recent_activity=1; user_session=5oxrsfsZCor1iJFCgRXXyeAXd8hcmzEUGh70-xHWLjQkT62Q; __Host-user_session_same_site=5oxrsfsZCor1iJFCgRXXyeAXd8hcmzEUGh70-xHWLjQkT62Q; logged_in=yes; dotcom_user=pengjunlee; _gat=1'
    cookies = {i.split('=')[0]: i.split('=')[1] for i in cookies.split('; ')}
    yield scrapy.Request(self.start_urls[0], cookies=cookies)
    
  def parse(self, response): # 验证是否请求成功
    print(re.findall('Learn Git and GitHub without any code!',response.body.decode()))

执行爬虫后,后台部分日志截图如下:

Scrapy实现模拟登录的示例代码

发送Post请求模拟登录

Scrapy还提供了两种通过发送Post请求来获取Cookies的方法。

scrapy.FormRequest()

使用scrapy.FormRequest()发送Post请求实现模拟登陆,需要人为找出登录请求的地址以及构造出登录时所需的请求数据。

使用scrapy.FormRequest()模拟登录Github的示例代码: 

# -*- coding: utf-8 -*-
import scrapy
import re
 
class GithubLoginSpider(scrapy.Spider):
  name = 'github_login'
  allowed_domains = ['github.com']
  start_urls = ['https://github.com/login']
 
  def parse(self, response): # 发送Post请求获取Cookies
    authenticity_token = response.xpath('//input[@name="authenticity_token"]/@value').extract_first()
    utf8 = response.xpath('//input[@name="utf8"]/@value').extract_first()
    commit = response.xpath('//input[@name="commit"]/@value').extract_first()
    form_data = {
      'login': 'pengjunlee@163.com',
      'password': '123456',
      'webauthn-support': 'supported',
      'authenticity_token': authenticity_token,
      'utf8': utf8,
      'commit': commit}
    yield scrapy.FormRequest("https://github.com/session", formdata=form_data, callback=self.after_login)
 
  def after_login(self, response): # 验证是否请求成功
    print(re.findall('Learn Git and GitHub without any code!', response.body.decode()))

从后台日志不难看出,Scrapy 在请求完 https://github.com/session 后,自动帮我们重定向到了Github首页。

Scrapy实现模拟登录的示例代码

scrapy.FormRequest.from_response()

scrapy.FormRequest.from_response()使用起来比 scrapy.FormRequest()更加简单方便,我们通常只需要提供用户相关信息(账户和密码)即可,scrapy.FormRequest.from_response()将通过模拟点击为我们填充好其他的表单字段并提交表单。

使用scrapy.FormRequest.from_response()模拟登录Github的示例代码: 

# -*- coding: utf-8 -*-
import scrapy
import re
 
class GithubLogin2Spider(scrapy.Spider):
  name = 'github_login2'
  allowed_domains = ['github.com']
  start_urls = ['https://github.com/login']
 
  def parse(self, response): # 发送Post请求获取Cookies
    form_data = {
      'login': 'pengjunlee@163.com',
      'password': '123456'
    }
    yield scrapy.FormRequest.from_response(response,formdata=form_data,callback=self.after_login)
 
  def after_login(self,response): # 验证是否请求成功
    print(re.findall('Learn Git and GitHub without any code!',response.body.decode()))

scrapy.FormRequest.from_response()方法还可以传入其他参数来帮我们更加精确的指定表单元素:

'''
response (Response object) ? 包含表单HTML的响应,将用来对表单的字段进行预填充
formname (string) ? 如果设置了该值,name 等于该值的表单将被使用
formid (string) ? 如果设置了该值,id 等于该值的表单将被使用
formxpath (string) ? 如果设置了该值,匹配该 xpath 的第一个表单将被使用
formcss (string) ? 如果设置了该值,匹配该 css选择器的第一个表单将被使用
formnumber (integer) ? 索引值等于该值的表单将被使用,默认第一个(索引值为 0 )
formdata (dict) ? 传入的表单数据,将覆盖form 元素中已经存在的值
clickdata (dict) ? 用于查找可点击控件的属性值
dont_click (boolean) ? 如果设置为 True,将不点击任何元素,直接提交表单数据
'''

参考文章

https://doc.scrapy.org/en/latest/topics/request-response.html

到此这篇关于Scrapy实现模拟登录的示例代码的文章就介绍到这了,更多相关Scrapy 模拟登录内容请搜索三水点靠木以前的文章或继续浏览下面的相关文章希望大家以后多多支持三水点靠木!

Python 相关文章推荐
python 图片验证码代码分享
Jul 04 Python
python在windows下实现ping操作并接收返回信息的方法
Mar 20 Python
Python functools模块学习总结
May 09 Python
在Python中使用next()方法操作文件的教程
May 24 Python
Pthon批量处理将pdb文件生成dssp文件
Jun 21 Python
Python中的条件判断语句与循环语句用法小结
Mar 21 Python
在python中pandas读文件,有中文字符的方法
Dec 12 Python
python zip()函数使用方法解析
Oct 31 Python
Python图像处理库PIL的ImageDraw模块介绍详解
Feb 26 Python
python:批量统计xml中各类目标的数量案例
Mar 10 Python
PyQT5 实现快捷键复制表格数据的方法示例
Jun 19 Python
Python实现http接口自动化测试的示例代码
Oct 09 Python
scrapy-splash简单使用详解
Feb 21 #Python
详解使用scrapy进行模拟登陆三种方式
Feb 21 #Python
利用Python如何画一颗心、小人发射爱心
Feb 21 #Python
python 第三方库paramiko的常用方式
Feb 20 #Python
Python中Qslider控件实操详解
Feb 20 #Python
python基于selenium爬取斗鱼弹幕
Feb 20 #Python
Python爬虫+Tkinter制作一个翻译软件的示例
Feb 20 #Python
You might like
关于PHP自动判断字符集并转码的详解
2013/06/26 PHP
php实现文件下载简单示例(代码实现文件下载)
2014/03/10 PHP
PHP获取youku视频真实flv文件地址的方法
2014/12/23 PHP
PHP随手笔记整理之PHP脚本和JAVA连接mysql数据库
2015/11/25 PHP
无阻塞加载脚本分析[全]
2011/01/20 Javascript
Extjs4 Treegrid 使用心得分享(经验篇)
2013/07/01 Javascript
AngularJS iframe跨域打开内容时报错误的解决办法
2015/01/26 Javascript
ECMAScript6函数剩余参数(Rest Parameters)
2015/06/12 Javascript
js检测iframe是否加载完成的方法
2015/11/26 Javascript
JS传递对象数组为参数给后端,后端获取的实例代码
2016/06/28 Javascript
浅谈JavaScript 覆盖原型以及更改原型
2016/08/31 Javascript
bootstrap modal弹出框的垂直居中
2016/12/14 Javascript
JS实现随机颜色的3种方法与颜色格式的转化
2017/01/05 Javascript
基于Node.js的WebSocket通信实现
2017/03/11 Javascript
vue 2.0路由之路由嵌套示例详解
2017/05/08 Javascript
AngularJS 验证码60秒倒计时功能的实现
2017/06/05 Javascript
AngularJS通过ng-Img-Crop实现头像截取的示例
2017/08/17 Javascript
react中fetch之cors跨域请求的实现方法
2018/03/14 Javascript
JavaScript去掉数组重复项的方法分析【测试可用】
2018/07/19 Javascript
解决Angular2 router.navigate刷新页面的问题
2018/08/31 Javascript
浅谈JavaScript 代码整洁之道
2018/10/23 Javascript
浅谈在不使用ssr的情况下解决Vue单页面SEO问题(2)
2018/11/08 Javascript
Vue3为什么这么快
2020/09/23 Javascript
Python爬取国外天气预报网站的方法
2015/07/10 Python
python实现八大排序算法(1)
2017/09/14 Python
Python3.6实现连接mysql或mariadb的方法分析
2018/05/18 Python
python如何生成网页验证码
2018/07/28 Python
python中用logging实现日志滚动和过期日志删除功能
2019/08/20 Python
python每5分钟从kafka中提取数据的例子
2019/12/23 Python
python实现超级马里奥
2020/03/18 Python
Python sublime安装及配置过程详解
2020/06/29 Python
容易被忽略的Python内置类型
2020/09/03 Python
size?瑞典:英国伦敦的球鞋精品店
2018/03/01 全球购物
2014年效能监察工作总结
2014/11/21 职场文书
2014年语文教研组工作总结
2014/12/06 职场文书
企业爱心捐款倡议书
2015/04/27 职场文书