python爬虫框架scrapy代理中间件掌握学习教程

Python爬虫框架Scrapy代理中间件掌握学习教程

在进行爬虫开发时,经常需要使用代理来避免IP被封锁或者提高爬取效率。而Scrapy是一个功能强大的Python爬虫框架,也提供了代理中间件这一强大的功能以支持代理。

代理中间件的使用方法

Scrapy提供了一个内置的代理中间件,可以通过在项目设置中设置代理中间件的位置及相应的参数,来让Scrapy使用代理。

以下是在Scrapy项目的settings.py中加入代理中间件的配置方法:

DOWNLOADER_MIDDLEWARES = {
    'scrapy.downloadermiddlewares.useragent.UserAgentMiddleware': None, #禁用默认的代理中间件
    'scrapy_proxy_pool.middlewares.ProxyPoolMiddleware': 610, #启用代理池中间件
    'scrapy_proxy_pool.middlewares.BanDetectionMiddleware': 620, #启用ban检测中间件
}
# scrapy-proxy-pool是一个常用的代理池,可通过pip安装
PROXY_POOL_ENABLED = True

以上配置中,我们禁用了Scrapy默认的代理中间件(内置的HttpProxyMiddleware和RetryMiddleware),启用了第三方的代理池中间件scrapy-proxy-pool,并设置了其在下载器中的顺序。

需要注意的是,要在使用代理之前先安装代理池模块 scrapy-proxy-pool

示例1:使用代理IP池来爬取网站

假设我们要使用代理来爬取一个目标网站,我们可以创建一个新的scrapy项目进行实验。以下是项目的目录结构(省略了一些不必要的文件和目录):

scrapy-proxy-example/
    scrapy.cfg
    proxy_example/
        __init__.py
        items.py
        middlewares.py
        pipelines.py
        settings.py
        spiders/
            __init__.py
            my_spider.py

首先,我们在settings.py中添加上述代理中间件配置。

然后,我们需要在middlewares.py中编写代理中间件,用来从代理池中获取IP,并添加到请求中:

import requests
from scrapy import signals
from scrapy.exceptions import NotConfigured
from scrapy.http import HtmlResponse
from fake_useragent import UserAgent

class ProxyPoolMiddleware(object):
    proxy_url = 'http://127.0.0.1:5555/random'

    def __init__(self):
        self.proxy = None

    def process_request(self, request, spider):
        if self.proxy and self._check_proxy(self.proxy):
            request.meta['proxy'] = self.proxy
        else:
            self.proxy = requests.get(self.proxy_url).text.strip()
            request.meta['proxy'] = self.proxy

    def process_response(self, request, response, spider):
        return response

    def process_exception(self, request, exception, spider):
        if self.proxy and self._check_proxy(self.proxy):
            request.meta['proxy'] = self.proxy
            return request
        else:
            self.proxy = requests.get(self.proxy_url).text.strip()
            request.meta['proxy'] = self.proxy
            return request

    def _check_proxy(self, proxy):
        try:
            requests.get('https://www.baidu.com/', proxies={'https': 'https://{}'.format(proxy)}, timeout=3)
            return True
        except:
            return False

在这个中间件中,我们定义了一个代理URL(proxy_url),每次发起请求时都会从这个URL获取一个新的代理IP。如果已经有可用的代理IP,则直接使用,否则通过请求获取新的IP,并设置到request.meta['proxy']中。

接下来,我们来创建一个Spider文件(my_spider.py)来爬取目标网站,使用刚刚编写的代理中间件,以下是my_spider.py的代码:

import scrapy
from proxy_example.items import ProxyExampleItem

class MySpider(scrapy.Spider):
    name = 'my_spider'
    allowed_domains = ['target_site.com']
    start_urls = ['https://www.target_site.com/']

    def parse(self, response):
        # 在这里解析网页内容
        pass

在Spider中,我们只关注如何解析目标网站的内容,而不用关心如何获取代理IP。

以上就是使用代理IP池来爬取网站的完整示例,如果需要获取更多代理IP池的使用信息,可以参考文献中提供的相关链接。

示例2:使用隧道代理来爬取网站

使用隧道代理是一种常见的代理方式,它可以让我们通过隧道链接来获取代理IP。以下是如何使用隧道代理来爬取网站的示例:

我们可以使用requests模块来实现一个获取隧道代理的函数:

def get_tunnel_proxy():
    proxy_host = 'https://proxyserver.com'
    proxy_port = 3128
    tunnel_host = 'tunnelserver.com'
    tunnel_port = 8080
    proxy_type = 'http'

    # 构造代理隧道连接
    session = requests.Session()
    session.proxies = {
        'http': 'http://{}:{}/'.format(proxy_host, proxy_port),
        'https': 'http://{}:{}/'.format(proxy_host, proxy_port),
    }
    session.headers.update({'Proxy-Connection': 'Keep-Alive'})
    session.get('http://{}'.format(tunnel_host), timeout=10)

    # 验证隧道代理
    try:
        requests.get('http://httpbin.org/ip', proxies={'http': proxy_type + '://{}:{}'.format(tunnel_host, tunnel_port)}, timeout=2)
        return '{}://{}:{}'.format(proxy_type, tunnel_host, tunnel_port)
    except Exception as e:
        print('Error:', e)
        return None

在这个函数中,我们通过构造了一个代理隧道连接,并利用获取的IP地址在隧道代理服务器中建立连接来验证代理的有效性,最终返回一个构造好的隧道代理IP(示例中使用的是HTTP代理)。

使用上述方法获取代理IP的过程可以在爬虫启动时进行,例如,我们可以在Spider类中加入相应的过程:

class MySpider(scrapy.Spider):
    name = 'my_spider'
    allowed_domains = ['target_site.com']
    start_urls = ['https://www.target_site.com/']

    def start_requests(self):
        self.proxy = get_tunnel_proxy() # 获取隧道代理IP
        yield scrapy.Request(
            self.start_urls[0],
            callback=self.parse,
            meta={
                'proxy': self.proxy,
            }   
        )

    def parse(self, response):
        # 在这里解析网页内容
        pass

在这个Spider中,我们重载了start_requests()函数,通过get_tunnel_proxy()方法获取代理IP,并将其设置到请求的meta中。这样,后续的请求都会通过获取的隧道代理IP来发起连接。

以上就是使用隧道代理来爬取网站的完整示例,更多的代理方式可以参考文献中提供的相关链接。

参考文献

  1. Scrapy官方文档中的代理设置
  2. scrapy-proxy-pool: 一款Scrapy代理池的扩展
  3. Python爬虫使用代理池
  4. 隧道代理介绍

本站文章如无特殊说明,均为本站原创,如若转载,请注明出处:python爬虫框架scrapy代理中间件掌握学习教程 - Python技术站

(0)
上一篇 2023年6月3日
下一篇 2023年6月3日

相关文章

  • 在Python中使用NumPy生成具有给定复数根的切比雪夫级数

    在Python中使用NumPy生成具有给定复数根的切比雪夫级数,需要遵循以下步骤: 第一步:导入必要的库 import numpy as np import matplotlib.pyplot as plt 第二步:定义函数 定义函数,生成切比雪夫级数,并返回其值。 def chebyshev_series(coeffs, x): ""&…

    python-answer 2023年3月25日
    00
  • Python自动化办公之生成PDF报告详解

    Python自动化办公之生成PDF报告详解 简介 本攻略将详细介绍如何使用Python语言自动化生成PDF报告。我们将使用Python中的reportlab库,Pillow库,以及Pandas库,通过数据处理和图表可视化来生成具有分析性质的PDF报告。 准备工作 在使用reportlab库来生成PDF文件之前,需要进行以下准备工作: 1.安装reportla…

    python 2023年6月5日
    00
  • python实现class对象转换成json/字典的方法

    想要将Python中的class对象转换成JSON或字典格式,可以使用Python内置的json模块来实现。 具体步骤如下: 在Python中导入json模块以及定义需要转换的class类。 import json class MyClass: def __init__(self, name, age): self.name = name self.age …

    python 2023年5月13日
    00
  • 如何解决cmd运行python提示不是内部命令

    如果在使用命令行或者终端(如cmd或者powershell)运行python脚本时出现“python不是内部或外部命令,也不是可运行的程序或批处理文件”错误,一般是环境变量设置不正确导致的。为了解决这个问题,我们需要按照以下步骤进行操作。 确定Python安装路径 首先需要确认Python的安装路径,比如在Windows系统上,Python通常安装在C盘Pr…

    python 2023年5月20日
    00
  • Python进阶之高级用法详细总结

    Python进阶之高级用法详细总结 1. 面向对象编程高级特性 1.1 继承 继承是面向对象编程中最常用的高级特性之一,它允许子类从父类中继承属性和方法。可以通过继承来避免重复编写代码,提高代码的复用性和可维护性。 下面是一个继承的示例: class Animal: def __init__(self, name): self.name = name def…

    python 2023年5月13日
    00
  • Python dict的使用误区你知道吗

    当我们使用Python开发过程中,使用Python字典是非常常见的。然而,许多开发者存在着困惑和误区,这会导致他们在编写代码的过程中出现各种问题。下面是Python dict使用误区的攻略。 误区1:认为字典是按顺序的 Python字典是无序的。虽然你在Python3.7中会发现字典数据会按特定的顺序打印,但实际上并没有保证字典的顺序。如果你需要按特定顺序处…

    python 2023年5月13日
    00
  • mysql巡检脚本(必看篇)

    让我详细为您讲解 “mysql巡检脚本(必看篇)” 的攻略。 1. 什么是 MySQL 巡检脚本? MySQL 巡检脚本是针对 MySQL 数据库的一个检测脚本,可以通过脚本检测 MySQL 数据库的运行情况,及时发现问题,并提供相应的解决方案,以确保 MySQL 数据库的稳定性及性能的优化。 2. MySQL 巡检脚本的功能特点 1) 安全检测 MySQL…

    python 2023年6月3日
    00
  • python入门教程 python入门神图一张

    Python入门教程 这篇文章是一张 Python 入门神图的详细讲解。Python 是一种高级编程语言,具有易读易写、简洁明了、可扩展性强等优势,在Web开发、科学计算、数据处理等领域广泛应用。 下面我们来一步一步学习这张 Python 入门神图。 第1步:安装Python Python官网提供了Windows、macOS、Linux等多种版本的安装包,你…

    python 2023年5月13日
    00
合作推广
合作推广
分享本页
返回顶部