python代理池的构建3——爬取代理ip

上篇博客地址python代理池的构建2——代理ip是否可用的处理和检查

一、基础爬虫模块(Base_spider.py)

#-*-coding:utf-8-*-
‘‘‘
目标: 实现可以指定不同URL列表,分组的XPATH和详情的XPATH,从不同页面上提取代理的IP,端口号和区域的通用爬虫;
步骤:
1.在base_ spider.py文件中,定义 一个BaseSpider类, 继承object

2.提供三个类成员变量:

    urls:代理IP网址的URL的列表

    group_ xpath:分组XPATH,获取包含代理IP信息标签列表的XPATH

    detail. xpath:组内XPATH,获取代理IP详情的信息XPATH,格式为: {‘ip‘:‘xx‘, ‘pot‘:‘xx‘,‘area‘:‘xx‘}

3.提供初始方法,传入爬虫URL列表,分组XPATH,详情(组内)XPATH4.对外提供-个获取代理IP的方法,遍历URL列表,获取URL

    根据发送请求,获取页面数据

    解析页面,提取数据,封装为Proxy对象

    返回Proxy对象列表

‘‘‘

import requests
import sys
from lxml import etree
sys.path.append("..")   #提供要导入的模块路径,之前博客讲过怎么使用
sys.path.append("../..")
from utils.http import get_requests_headers
from domain import Proxy

class BaseSpider(object):  #定义一个最基础的爬虫,后面爬取专门网站的爬虫继承这个基础爬虫
    urls = []
    group_xpath = ‘‘  #因为我们用的lxml模块解析页面,所以要传入分组xpath和细节xpath
    detail_xpath = {}  #这个细节xpath就是ip在页面的位置,端口在页面的位置等等

    def __init__(self,urls=[],group_xpath=‘‘,detail_xpath={}):
        if urls:
            self.urls = urls

        if group_xpath:
            self.group_xpath = group_xpath

        if detail_xpath:
            self.detail_xpath = detail_xpath

    def get_page_from_url(self,url):
        response = requests.get(url,headers=get_requests_headers())
        #这个get_requests_headers方法是获取一个随机请求头,之前http.py模块定义过这个方法
        return response.content

    def get_first_list(self,li=[]):
        if len(li)!=0:
            return li[0]
        else :
            return ‘‘

    def get_proxies_from_page(self,page):
        #这个就是把HTML页面给lxml,让它解析
        element = etree.HTML(page)

        trs = element.xpath(self.group_xpath)
        #print(trs)
        for tr in trs:
            #tr.xpath(self.detail_xpath[‘ip‘])因为这一部分返回的是一个列表,而且如果我们直接写
            #tr.xpath(self.detail_xpath[‘ip‘])[0],如果这个列表为空,他就会报错导致程序异常终止
            ip = self.get_first_list(tr.xpath(self.detail_xpath[‘ip‘]))
            port = self.get_first_list(tr.xpath(self.detail_xpath[‘port‘]))
            area = self.get_first_list(tr.xpath(self.detail_xpath[‘area‘]))
            proxy = Proxy(ip,port,area=area)
            print(proxy.__dict__) #这个dict函数就是把对象转化成字典类型输出,python内部函数
            yield proxy  #函数有了这个关键字,函数就是一个生成器函数。上篇博客讲过,会挂一下链接

    def get_proxies(self):
        for url in self.urls:
            # print(url)
            page = self.get_page_from_url(url)
            # print(page)
            proxies = self.get_proxies_from_page(page)
            yield from proxies

if __name__ == ‘__main__‘: #用于测试这个这个模块
    # config = {
    #     ‘urls‘:{‘http://www.ip3366.net/?stype=1&page={}‘.format(i) for i in range(1,3)},
    #     ‘group_xpath‘:‘//*[@id="list"]/table/tbody/tr‘,
    #     ‘detail_xpath‘:{
    #         ‘ip‘:‘./td[1]/text()‘,
    #         ‘port‘:‘./td[2]/text()‘,
    #         ‘area‘:‘./td[6]/text()‘
    #     }
    # }
    #
    # spider = BaseSpider(**config)
    # for proxy in spider.get_proxies():
    #     print(proxy)
    url = ‘http://www.66ip.cn/4.html‘
    response = requests.get(url,headers=get_requests_headers())
    print(response.content.decode(‘GBK‘))

python 引用(import)文件夹下的py文件

二、专门针对几个网站的爬虫(proxy_spiders.py)

#-*-coding:utf-8-*-
from base_spider import BaseSpider

class XiciSpider(BaseSpider):
    urls = {‘https://www.xicidaili.com/nn/{}‘.format(i) for i in range(1,2)}
    group_xpath = ‘//*[@id="ip_list"]/tr[position()>1]‘
    detail_xpath = {
        ‘ip‘:‘./td[2]/text()‘,
        ‘port‘:‘./td[3]/text()‘,
        ‘area‘:‘./td[4]/a/text()‘
    }

class ProxylistplusSpider(BaseSpider):
    urls = {‘https://list.proxylistplus.com/Fresh-HTTP-Proxy-List-{}‘.format(i) for i in range(1,2)}
    group_xpath = ‘//*[@id="page"]/table[2]/tr[position()>5]‘
    detail_xpath = {
        ‘ip‘:‘./td[2]/text()‘,
        ‘port‘:‘./td[3]/text()‘,
        ‘area‘:‘./td[5]/text()‘
    }

class KuaidailiSpider(BaseSpider):
    urls = {‘https://www.kuaidaili.com/free/inha/{}‘.format(i) for i in range(1,4)}
    group_xpath = ‘//*[@id="list"]/table/tbody/tr‘
    detail_xpath = {
        ‘ip‘:‘./td[1]/text()‘,
        ‘port‘:‘./td[2]/text()‘,
        ‘area‘:‘./td[5]/text()‘

    }

class ip66Spider(BaseSpider):
    urls = {‘http://www.66ip.cn/{}.html‘.format(i) for i in range(1,4)}
    group_xpath = ‘//*[@id="main"]/div/div[1]/table/tr[position()>1]‘
    detail_xpath = {
        ‘ip‘:‘./td[1]/text()‘,
        ‘port‘:‘./td[2]/text()‘,
        ‘area‘:‘./td[3]/text()‘
    }

if __name__ == ‘__main__‘:
    pass
    # spider = XiciSpider()
    # spider = ProxylistplusSpider()
    # spider = KuaidailiSpider()
    #  spider = ip66Spider()
    #  for proxy in spider.get_proxies():
    #      print(proxy)

我写的时候就没遇到反爬。。。。我也不知道为啥。。。。我就传了一个请求头headers

三、运行这几个爬虫(run_spiders.py)

#-*-coding:utf-8-*-
import sys
import importlib
import schedule
import time
from gevent import monkey
monkey.patch_all()  #打上猴子补丁,这个我博客下面有这一方面解释链接

from gevent.pool import Pool   #导入协程池
#可能有人会问为什么要用协程,因为requests.get()请求的时候会等待时间,我们可以利用这一部分时间做其他事情
sys.path.append("../..")
sys.path.append("..")
from settings import SPIDERS
from proxy_validate.httpbin_validator import check_proxy
from db.mongo_pool import MongoPool  #要把可用代理IP存入mongodb数据库
from utils.log import logger
from settings import RUN_SPIDERS_INTERVAL #这些都是settings.py模块的一些变量

class RunSpiders(object):

    def __init__(self):
        self.mongo_pool = MongoPool()  #创建一个数据库对象,这个是我们写的模块,可以看python代理池的构建4——mongdb数据库的增删改查
        self.coroutine_pool = Pool() #创建协程池

    def get_spider_from_settings(self):
        for full_class_name in SPIDERS:  #下面这一部分就是动态导入模块,我会给出相应博客链接去解释他
            module_name,class_name=full_class_name.rsplit(‘.‘,maxsplit=1)
            module = importlib.import_module(module_name)
            clss = getattr(module,class_name)
            spider = clss()
            #print(spider)
            yield spider

    def run(self):
        spiders = self.get_spider_from_settings()

        for spider in spiders:  #开启多协程去分别运行多个爬虫
            self.coroutine_pool.apply_async(self.run_one,args=(spider,))

        self.coroutine_pool.join()  #等全部爬虫都运行完,再结束这个函数

    def run_one(self,spider):
        try:   #try一下,以防某个爬虫失败导入异常,从而程序异常结束
            for proxy in spider.get_proxies():
                proxy = check_proxy(proxy)
                if proxy.speed != -1:
                    self.mongo_pool.insert_one(proxy)  #这个就是把这一个代理ip信息插入到数据库里面
        except Exception as ex:
            logger.exception(ex)

    @classmethod  #定义一个类方法,之后可以通过类名来调用
    def start(cls):  #这个cls参数,是它自己就带的
        rs = RunSpiders()
        rs.run()
        schedule.every(RUN_SPIDERS_INTERVAL).hours.do(rs.run)
        #这个意思就是每隔RUN_SPIDERS_INTERVAL小时,就执行一遍rs.run函数
        while True:
            schedule.run_pending()  #这个就是检查时间到两个小时了没
            time.sleep(60)

if __name__ == ‘__main__‘:   #检查本模块是否可用
    RunSpiders.start()
    # rs = RunSpiders()
    # rs.run()

四、关于代码一些问题解决链接:

协程gevent模块和猴子补丁

python中schedule模块的简单使用 || importlib.import_module动态导入模块

Python中“*”和“**”的用法 || yield的用法 || ‘$in’和‘$nin‘ || python @property的含义

python代理池的构建4——mongdb数据库的增删改查

五、python代理池的构建的其他链接

python代理池的构建5——对mongodb数据库里面代理ip检查

python代理池的构建4——mongdb数据库的增删改查

python代理池的构建2——代理ip是否可用的处理和检查

python代理池的构建1——代理IP类的构建,以及配置文件、日志文件、requests请求头

原文地址:https://www.cnblogs.com/kongbursi-2292702937/p/12174610.html

时间: 2024-11-06 09:52:38

python代理池的构建3——爬取代理ip的相关文章

python代理池的构建2——代理ip是否可用的处理

上一篇博客地址:python代理池的构建1——代理IP类的构建,以及配置文件.日志文件.requests请求头 一.代理ip是否可用的处理 #-*-coding:utf-8-*- #check ip ''' 目标:检查代理IP速度,匿名程度以及支持的协议类型. 步骤: 检查代理IP速度和匿名程度; 代理IP速度:就是从发送请求到获取响应的时间间隔 匿名程度检查: 对http://httpbin.org/get 或https://httpbin.org/get 发送请求 如果响应的origin 中

python爬虫爬取代理IP

# #author:wuhao # #--*------------*-- #-****#爬取代理IP并保存到Excel----#爬取当日的代理IP并保存到Excel,目标网站xicidaili.com#如果访问频率太快的话,会被网站封掉IP import urllib.request import urllib.parse import re import xlwt import http.cookiejar import datetime from bs4 import BeautifulS

python爬取代理ip

要写爬虫爬取大量的数据,就会面临ip被封的问题,虽然可以通过设置延时的方法来延缓对网站的访问,但是一旦访问次数过多仍然会面临ip被封的风险,这时我们就需要用到动态的ip地址来隐藏真实的ip信息,如果做爬虫项目,建议选取一些平台提供的动态ip服务,引用api即可.目前国内有很多提供动态ip的平台,普遍价格不菲,而对于只想跑个小项目用来学习的话可以参考下本篇文章. 简述 本篇使用简单的爬虫程序来爬取免费ip网站的ip信息并生成json文档,存储可用的ip地址,写其它爬取项目的时候可以从生成的json

【python爬虫】根据查询词爬取网站返回结果

最近在做语义方面的问题,需要反义词.就在网上找反义词大全之类的,但是大多不全,没有我想要的.然后就找相关的网站,发现了http://fanyici.xpcha.com/5f7x868lizu.html,还行能把"老师"-"学生","医生"-"病人"这样对立关系的反义词查出来. 一开始我想把网站中数据库中存在的所有的词语都爬出来(暗网爬虫),但是分析了url的特点: http://fanyici.xpcha.com/5f7x86

python爬虫实例详细介绍之爬取大众点评的数据

python 爬虫实例详细介绍之爬取大众点评的数据 一. Python作为一种语法简洁.面向对象的解释性语言,其便捷性.容易上手性受到众多程序员的青睐,基于python的包也越来越多,使得python能够帮助我们实现越来越多的功能.本文主要介绍如何利用python进行网站数据的抓取工作.我看到过利用c++和Java进行爬虫的代码,c++的代码很复杂,而且可读性.可理解性较低,不易上手,一般是那些高手用来写着玩加深对c++的理解的,这条路目前对我们不通.Java的可读性还可以,就是代码冗余比较多,

怎么来爬取代理服务器ip地址?

一年前突然有个灵感,想搞个强大的网盘搜索引擎,但由于大学本科学习软件工程偏嵌入式方向,web方面的能力有点弱,不会jsp,不懂html,好久没有玩过sql,但就是趁着年轻人的这股不妥协的劲儿,硬是把以前没有学习的全部给学了一遍,现在感觉web原来也就那么回事.好了,废话就不说了,看到本文的读者,可以先看看我做的东西:去转盘网 ok搜搜:www.oksousou.com(这个是磁力,顺便拿出来给大伙观赏) 言归正传,由于我要爬取百度网盘,而度娘你懂的的搞爬虫出生的,反爬虫的能力很牛掰.尤其像我用我

python代理池的构建1——代理IP类的构建,以及配置文件、日志文件、requests请求头

一.整体结构 二.代理IP类的构建(domain.py文件) ''' 实现_ init_ 方法, 负责初始化,包含如下字段: ip: 代理的IP地址 port:代理IP的端口号 protocol: 代理IP支持的协议类型,http是0, https是1, https和http都支持是2 nick_ type: 代理IP的匿名程度,高匿:0,匿名: 1,透明:2 speed:代理IP的响应速度,单位s area:代理IP所在地区 score:代理IP的评分,用于衡量代理的可用性;默认分值可以通过配

大神教你如果学习Python爬虫 如何才能高效地爬取海量数据

Python如何才能高效地爬取海量数据 我们都知道在互联网时代,数据才是最重要的,而且如果把数据用用得好的话,会创造很大的价值空间.但是没有大量的数据,怎么来创建价值呢?如果是自己的业务每天都能产生大量的数据,那么数据量的来源问题就解决啦,但是没有数据怎么办??哈哈哈,靠爬虫来获取呀!!! 通过利用爬虫技术获取规模庞大的互联网数据,然后做市场分析.竞品调研.用户分析.商业决策等. 也许对于小白来说,爬虫是一件非常难且技术门槛高的是,但是如果掌握了正确的方法,在短时间内可以让你应运自如.下面就分享

23个Python爬虫开源项目代码:爬取微信、淘宝、豆瓣、知乎、微博等

来源:全球人工智能 作者:SFLYQ 今天为大家整理了23个Python爬虫项目.整理的原因是,爬虫入门简单快速,也非常适合新入门的小伙伴培养信心.所有链接指向GitHub,祝大家玩的愉快 1.WechatSogou [1]– 微信公众号爬虫. 基于搜狗微信搜索的微信公众号爬虫接口,可以扩展成基于搜狗搜索的爬虫,返回结果是列表,每一项均是公众号具体信息字典. github地址:https://github.com/Chyroc/WechatSogou 2.DouBanSpider [2]– 豆瓣