爬虫笔记

xpath 工具,获取HTML元素

节点修饰符

/ 根节点,(最外层元素标签)

// 子节点(相对路劲)

. 当前路径

.. 上一次路径

@xx 获取节点的属性

text() 获取值

包含语法(contains),包含部分就能够查找所有 //div[contains(@id,"qiushi_tag_")] (糗事百科)

数据解析方法

主要有结构化和非结构化分类

结构化:

​ json数据(高拼出现)

​ json 模块

​ re 模块

​ jsonpath模块

​ xml 数据 (低频出现)

​ re 模块

​ lxml 模块

非结构化

​ html

​ re 模块

​ lxml模块

服务器反爬的原因

1 爬虫占的PV(页面的访问次数, 每打开刷新一个页面的话,就占一个pv)总数较高,浪费资源

2 三月爬虫 , 毕业生在写论文的时候,会进行爬取一些网站数据,在进行分析

3 法律的灰色地带

爬虫反反爬机制

1 设置 headers 请求头(异步请求等) 和 设置 referew字段(从哪来发起的请求)

2 通过cookie来进行反爬

3 通过请求的参数来进行反爬

​ 1根据html文件提取

​ 2 通过发送请求获取数据

​ 3 通过js来生成参数 (分析js,通过js2py获取js执行结果,或使用selenium)

​ 4 验证码 (打码平台)

4 更换ip代理

scrapy 框架

  • 1 scrapy 框架 是python开源 编写一个网络爬虫框架

网络爬虫的流程

image-20200719213943828

流程:

1 首先我们有起始的url

​ 2 拿到起始的url后放到URL队列,从队列中拿到URL发送网络请求获取响应

​ 3 拿到请求响应后进行 解析响应内容,如果解析的是数据,那么将数据保存, 如果解析的 是url的话 返回给url队列,进行一个循环操作

scrapy 框架工作流程

image-20200719220248584

简易理解

image-20200719214344254

工作流程步骤:

​ 1首先拿到起始的url 通过 scrapy 引擎(中间件)传递 到url队列中

​ 2 从url 队列 拿出起始的url 给 发送请求获取响应(下载器), 得到响应对象之后 通过 scrapy 引擎 (中间件)传递给解析响应对象

​ 3 解析响应对象,如果解析出新的URL对象之后 会再次给 url队列中,如果解析的是数据的 话 会拿给 scrapy 引擎(中间件)item poplin (管道)做 数据的保存或过滤

抽象讲 scrapy 工作原理

image-20200719220248584

image-20200719221915624

scrapy Engine (引擎)负责调度 各种模块的运行

Scheduler(调度器)接收引擎发送过来的request请求

spiders (爬虫) 负责处理解析出所有的数据和url,并将解析到新的URL提交给引擎,再次进入Scheduler(调度器)

Downloader (下载器)接收scrapy引擎发送过来的 url 进行发送请求获取响应

item pipeline (管道)负责处理 spiders 发送的过来的数据,进行保存。

scrapy 中每个模块的作用

image-20200719222413933

创建项目

image-20200720092205172

创建爬虫项目

scrapy startproject [项目名]

创建爬虫

cd 进入 爬虫项目

scrapy genspider [爬虫名字] [域名]

运行爬虫命令

scrapy crawl [爬虫名字]

定义元素以及提取数据,属性值的方法

从xpath 对象中提取数据 extract() 和 extract_first()

解析response并获取scrapy爬虫中的数据: 利用xpath规则字符串进行定位和提取

response.xpath方法的返回结果是一个类似list的类型,其中包含的是selector对象,操作和列表一样,但是有一些额外的方法

提取数据:

​ 额外方法extract():返回一个包含有字符串的列表

​ 额外方法extract_first():返回列表中的第一个字符串,列表为空没有返回None

response响应对象的常用属性:

​ response.url:当前响应的url地址

​ response.request.url:当前响应对应的请求的url地址

​ response.headers:响应头

​ response.request.headers:当前响应的请求头

​ response.body:响应体,也就是html代码,byte类型

​ response.status:响应状态码

注意: 如果要存储数据的话,需要通过pipeline来保存数据。

函数中的yield能够传递的对象只能是:BaseItem, Request, dict, None

2 建模 可以通过items.py中建立所需的字段。然后在spider 中调用在使用.

3 meta:实现数据在不同的解析函数中传递,meta默认带有部分数据,比如下载延迟,请求深度等

在爬虫文件的parse方法中,提取详情页增加之前callback指定的parse_detail函数:

def parse(self,response):
    ...
    yield scrapy.Request(detail_url, callback=self.parse_detail,meta={"item":item})
...

def parse_detail(self,response):
    #获取之前传入的item
    item = resposne.meta["item"]

特别注意

  1. meta参数是一个字典
  2. meta字典中有一个固定的键proxy,表示代理ip,关于代理ip的使用我们将在scrapy的下载中间件的学习中进行介绍

scrape 获取cookie模拟登陆

第一种方法,使用的是直接获取cookie登录

第二种方法 通过scrapy.FormRequest能够发送post请求,同时需要添加fromdata参数作为请求体,以及callback

# 模拟登陆 GitHub,使用的是scrapy框架
import re

import scrapy


class GithubSpider(scrapy.Spider):
    name = 'github'
    allowed_domains = ['github.com']
    start_urls = ['http://github.com/login']

    # tARzc847MynkgK1DIeayOZMQHNNN22tj0usmHmGy4BjZ0gvpjWfxDefFqqf9BL9pgKGwJq2DTUHZG6itMmxdMA==
    def parse(self, response):
        token = response.xpath("//*[@id='login']/form/input[1]/@value").extract_first()
        # 获取登录响应解析post的数据
        data = {
            "commit": "Sign in",
            "authenticity_token": token,
            "login": "xiaohua439912875",
            "password": "kongguanghua520",
            "webauthn-support": "supported"
        }

        # 2 根据url进行post请求
        yield scrapy.FormRequest(
            url="http://github.com/session",
            formdata=data,
            callback=self.parse_login
        )

    def parse_login(self, response):
        match = re.search(r'"user-login" content="(.*?)"', response.text)
        user_name = match.group(1)
        print('UserName:', user_name)

posted @ 2020-08-27 11:49  阿Hua  阅读(208)  评论(0编辑  收藏  举报