python爬虫构建代理ip池抓取数据库的示例代码


Posted in Python onSeptember 22, 2020

爬虫的小伙伴,肯定经常遇到ip被封的情况,而现在网络上的代理ip免费的已经很难找了,那么现在就用python的requests库从爬取代理ip,创建一个ip代理池,以备使用。

本代码包括ip的爬取,检测是否可用,可用保存,通过函数get_proxies可以获得ip,如:{'HTTPS': '106.12.7.54:8118'}

下面放上源代码,并详细注释:

import requests
from lxml import etree
from requests.packages import urllib3
import random, time
 
urllib3.disable_warnings()
 
 
def spider(pages, max_change_porxies_times=300):
  """
  抓取 XiciDaili.com 的 http类型-代理ip-和端口号
 
  将所有抓取的ip存入 raw_ips.csv 待处理, 可用 check_proxies() 检查爬取到的代理ip是否可用
  -----
  :param pages:要抓取多少页
  :return:无返回
  """
  s = requests.session()
  s.trust_env = False
  s.verify = False
  urls =com/nn/{}'
  proxies = {}
  try_times = 0
  for i in range(pages):
    url = urls.format(i + 1)
    s.headers = {
      'Accept': 'text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,image/apng,*/*;q=0.8',
      'Accept-Encoding': 'gzip, deflate, br',
      'Accept-Language': 'zh-CN,zh;q=0.9',
      'Connection': 'keep-alive',
      'Referer': urls.format(i if i > 0 else ''),
      'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/68.0.3440.75 Safari/537.36'}
    while True:
      content = s.get(url, headers=s.headers, proxies=proxies)
      time.sleep(random.uniform(1.5, 4)) # 每读取一次页面暂停一会,否则会被封
      if content.status_code == 503: # 如果503则ip被封,就更换ip
        proxies = get_proxies()
        try_times += 1
        print(f'第{str(try_times):0>3s}次变更,当前{proxies}')
        if try_times > max_change_porxies_times:
          print('超过最大尝试次数,连接失败!')
          return -1
        continue
      else:
        break # 如果返回码是200 ,就跳出while循环,对爬取的页面进行处理
 
    print(f'正在抓取第{i+1}页数据,共{pages}页')
    for j in range(2, 102): # 用简单的xpath提取http,host和port
      tree = etree.HTML(content.text)
      http = tree.xpath(f'//table[@id="ip_list"]/tr[{j}]/td[6]/text()')[0]
      host = tree.xpath(f'//table[@id="ip_list"]/tr[{j}]/td[2]/text()')[0]
      port = tree.xpath(f'//table[@id="ip_list"]/tr[{j}]/td[3]/text()')[0]
      check_proxies(http, host, port) # 检查提取的代理ip是否可用
 
 
def check_proxies(http, host, port, test_url='http://www.baidu.com'):
  """
  检测给定的ip信息是否可用
 
  根据http,host,port组成proxies,对test_url进行连接测试,如果通过,则保存在 ips_pool.csv 中
  :param http: 传输协议类型
  :param host: 主机
  :param port: 端口号
  :param test_url: 测试ip
  :return: None
  """
  proxies = {http: host + ':' + port}
  try:
    res = requests.get(test_url, proxies=proxies, timeout=2)
    if res.status_code == 200:
      print(f'{proxies}检测通过')
      with open('ips_pool.csv', 'a+') as f:
        f.write(','.join([http, host, port]) + '\n')
  except Exception as e: # 检测不通过,就不保存,别让报错打断程序
    print(e)
 
 
def check_local_ip(fn, test_url):
  """
  检查存放在本地ip池的代理ip是否可用
 
  通过读取fn内容,加载每一条ip对test_url进行连接测试,链接成功则储存在 ips_pool.csv 文件中
  :param fn: filename,储存代理ip的文件名
  :param test_url: 要进行测试的ip
  :return: None
  """
  with open(fn, 'r') as f:
    datas = f.readlines()
    ip_pools = []
  for data in datas:
    # time.sleep(1)
    ip_msg = data.strip().split(',')
    http = ip_msg[0]
    host = ip_msg[1]
    port = ip_msg[2]
    proxies = {http: host + ':' + port}
    try:
      res = requests.get(test_url, proxies=proxies, timeout=2)
      if res.status_code == 200:
        ip_pools.append(data)
        print(f'{proxies}检测通过')
        with open('ips_pool.csv', 'a+') as f:
          f.write(','.join([http, host, port]) + '\n')
    except Exception as e:
      print(e)
      continue
 
 
def get_proxies(ip_pool_name='ips_pool.csv'):
  """
  从ip池获得一个随机的代理ip
  :param ip_pool_name: str,存放ip池的文件名,
  :return: 返回一个proxies字典,形如:{'HTTPS': '106.12.7.54:8118'}
  """
  with open(ip_pool_name, 'r') as f:
    datas = f.readlines()
  ran_num = random.choice(datas)
  ip = ran_num.strip().split(',')
  proxies = {ip[0]: ip[1] + ':' + ip[2]}
  return proxies
 
 
if __name__ == '__main__':
  t1 = time.time()
  spider(pages=3400)
  t2 = time.time()
  print('抓取完毕,时间:', t2 - t1)
 
  # check_local_ip('raw_ips.csv','http://www.baidu.com')

以上就是python爬虫构建代理ip池抓取数据库的示例代码的详细内容,更多关于python爬虫构建代理ip池的资料请关注三水点靠木其它相关文章!

Python 相关文章推荐
python用模块zlib压缩与解压字符串和文件的方法
Dec 16 Python
Python求解任意闭区间的所有素数
Jun 10 Python
Pycharm更换python解释器的方法
Oct 29 Python
python代码 输入数字使其反向输出的方法
Dec 22 Python
python requests.post带head和body的实例
Jan 02 Python
Python面向对象程序设计示例小结
Jan 30 Python
python操作日志的封装方法(两种方法)
May 23 Python
详解Python中的各种转义符\n\r\t
Jul 10 Python
python-sys.stdout作为默认函数参数的实现
Feb 21 Python
python 操作mysql数据中fetchone()和fetchall()方式
May 15 Python
详解Pymongo常用查询方法总结
Jan 29 Python
详解Python+OpenCV进行基础的图像操作
Feb 15 Python
scrapy中如何设置应用cookies的方法(3种)
Sep 22 #Python
Python浮点型(float)运算结果不正确的解决方案
Sep 22 #Python
如何使用PyCharm引入需要使用的包的方法
Sep 22 #Python
python 如何区分return和yield
Sep 22 #Python
Python中三维坐标空间绘制的实现
Sep 22 #Python
Pyinstaller打包Scrapy项目的实现步骤
Sep 22 #Python
Python使用pickle进行序列化和反序列化的示例代码
Sep 22 #Python
You might like
解析php中die(),exit(),return的区别
2013/06/20 PHP
解析php中如何调用用户自定义函数
2013/08/06 PHP
PHPExcel读取EXCEL中的图片并保存到本地的方法
2015/02/14 PHP
自制PHP框架之路由与控制器
2017/05/07 PHP
PHP获取数组中单列值的方法
2017/06/10 PHP
PHP用continue跳过本次循环中剩余代码的注意点
2017/06/27 PHP
PHP实现微信退款功能
2018/10/02 PHP
PHP应用跨时区功能的实现方法
2019/03/21 PHP
PHP实现批量修改文件名的方法示例
2019/09/18 PHP
Ctrl+Enter提交内容信息
2006/06/26 Javascript
Javascript 匿名函数及其代码模式原理
2010/03/19 Javascript
提升你网站水平的jQuery插件集合推荐
2011/04/19 Javascript
JS字符串函数扩展代码
2011/09/13 Javascript
jQuery利用sort对DOM元素进行排序操作
2016/11/07 Javascript
js实现导航吸顶效果
2017/02/24 Javascript
webpack独立打包和缓存处理详解
2017/04/03 Javascript
Vue.js实战之组件的进阶
2017/04/04 Javascript
详解es6超好用的语法糖Decorator
2018/08/01 Javascript
jQuery实现高级检索功能
2019/05/28 jQuery
js 对象使用的小技巧实例分析
2019/11/08 Javascript
bootstrap-table后端分页功能完整实例
2020/06/01 Javascript
Python多线程编程(八):使用Event实现线程间通信
2015/04/05 Python
详解Python中的条件判断语句
2015/05/14 Python
新手如何快速入门Python(菜鸟必看篇)
2017/06/10 Python
python给微信好友定时推送消息的示例
2019/02/20 Python
django框架实现一次性上传多个文件功能示例【批量上传】
2019/06/19 Python
python flask框架实现重定向功能示例
2019/07/02 Python
详解python statistics模块及函数用法
2019/10/27 Python
Keras loss函数剖析
2020/07/06 Python
Python常驻任务实现接收外界参数代码解析
2020/07/21 Python
利用CSS3实现文本框的清除按钮相关的一些效果
2015/06/23 HTML / CSS
2014年高一班主任工作总结
2014/12/05 职场文书
新员工试用期工作总结2015
2015/05/28 职场文书
学校2016年圣诞节活动总结
2016/03/31 职场文书
uniapp开发小程序的经验总结
2021/04/08 Javascript
Redis实战高并发之扣减库存项目
2022/04/14 Redis