Python实现代理IP扫描与可用性验证完整教程
本文介绍如何使用Python编写工具扫描并获取可用的代理IP。通过解析西刺代理网站结构,利用requests和BeautifulSoup提取IP、端口及协议信息,并结合多线程与队列机制提高抓取效率。随后通过请求特定网站验证代理有效性,最终将可用代理保存至文件,适用于需要大量代理资源的爬虫场景。
本文介绍一个实用的网络工具,用于扫描并获取可用的代理IP。
首先,以http://www.xicidaili.com网站为例进行演示。
该网站提供了大量国内外可用的代理IP及其对应端口。
按照常规分析流程,我们首先针对国内代理部分进行扫描。
通过审查国内代理页面的结构,发现其URL遵循特定规律。
具体URL格式为http://www.xicidaili.com/nn/x。
其中x代表页码,该网站约有两千多页,因此需要采用线程处理以提高效率。
尝试直接使用最简单的requests.get()方法获取页面内容。
直接请求返回503错误状态码。
为此,我们需要添加简单的headers请求头,此时返回200状态码,表示请求成功。
接下来对网页内容进行解析,以提取所需信息。
分析发现,包含IP信息的数据位于<tr>标签内,可以使用BeautifulSoup(bs)方便地提取标签内容。
进一步观察发现,IP、端口和协议信息分别位于提取出的<tr>标签内的第2、3、6个<td>标签中。
基于上述分析,制定如下编写思路。
处理页面时,首先提取所有tr标签,然后对每个tr标签中的td标签进行二次提取。
因此需要执行两次bs操作,且第二次操作前需将对象转换为字符串(str处理)。
由于获取tr后需要提取其中索引为2、3、6的元素。
但在for循环中直接输出i无法直接进行索引操作。
因此,对每个td的soup对象进行第二次操作后,直接提取索引为2、3、6的元素。
提取后,通过.string属性直接获取文本内容。
r = requests.get(url = url,headers = headers)
soup = bs(r.content,"html.parser")
data = soup.find_all(name = 'tr',attrs = {'class':re.compile('|[^odd]')})
for i in data:
soup = bs(str(i),'html.parser')
data2 = soup.find_all(name = 'td')
ip = str(data2[1].string)
port = str(data2[2].string)
types = str(data2[5].string).lower()
proxy = {}
proxy[types] = '%s:%s'%(ip,port)
这样,每次循环都能生成对应的proxy字典,供后续验证IP可用性使用。
在构建字典时需注意,需将协议类型(types)转换为小写。因为requests库的proxies参数中协议名称应为小写,而网页抓取的内容通常为大写,因此进行了大小写转换处理。
接下来探讨验证IP可用性的思路。
方法很简单,使用get方法并传入代理,请求特定网站。
目标网站为http://1212.ip138.com/ic.asp。
这是一个用于返回用户外网IP地址的网站。
url = 'http://1212.ip138.com/ic.asp' r = requests.get(url = url,proxies = proxy,timeout = 6)
在此步骤中,需设置timeout参数以去除响应时间过长的代理,此处设置为6秒。
以单个IP为例进行尝试,并分析返回的页面内容。
返回的内容格式如下。
<html> <head> <meta xxxxxxxxxxxxxxxxxx> <title> 您的IP地址 </title> </head> <body style="margin:0px"><center>您的IP是:[xxx.xxx.xxx.xxx] 来自:xxxxxxxx</center></body></html>
我们只需提取网页内容中[]内的部分即可。
如果代理可用,返回的内容将包含该代理的IP地址。
注意:有时返回的地址可能是本机外网IP,这种情况通常意味着代理不可用,因此需将其排除。
据此进行判断:如果返回的IP与proxy字典中的IP一致,则认为该IP为可用代理,并将其写入文件。
整体思路如上,最后结合queue和threading进行多线程处理。
具体代码如下。
#coding=utf-8
import requests
import re
from bs4 import BeautifulSoup as bs
import Queue
import threading
class proxyPick(threading.Thread):
def __init__(self,queue):
threading.Thread.__init__(self)
self._queue = queue
def run(self):
while not self._queue.empty():
url = self._queue.get()
proxy_spider(url)
def proxy_spider(url):
headers = {
.......
}
r = requests.get(url = url,headers = headers)
soup = bs(r.content,"html.parser")
data = soup.find_all(name = 'tr',attrs = {'class':re.compile('|[^odd]')})
for i in data:
soup = bs(str(i),'html.parser')
data2 = soup.find_all(name = 'td')
ip = str(data2[1].string)
port = str(data2[2].string)
types = str(data2[5].string).lower()
proxy = {}
proxy[types] = '%s:%s'%(ip,port)
try:
proxy_check(proxy,ip)
except Exception,e:
print e
pass
def proxy_check(proxy,ip):
url = 'http://1212.ip138.com/ic.asp'
r = requests.get(url = url,proxies = proxy,timeout = 6)
f = open('E:/url/ip_proxy.txt','a+')
soup = bs(r.text,'html.parser')
data = soup.find_all(name = 'center')
for i in data:
a = re.findall(r'\[(.*?)\]',i.string)
if a[0] == ip:
#print proxy
f.write('%s'%proxy+'\n')
print 'write down'
f.close()
#proxy_spider()
def main():
queue = Queue.Queue()
for i in range(1,2288):
queue.put('http://www.xicidaili.com/nn/'+str(i))
threads = []
thread_count = 10
for i in range(thread_count):
spider = proxyPick(queue)
threads.append(spider)
for i in threads:
i.start()
for i in threads:
i.join()
print "It's down,sir!"
if __name__ == '__main__':
main()
通过上述代码,即可将网站上所有能用的代理IP全部写入ip_proxy.txt文件中。
以上Python扫描代理并获取可用IP的实例分享完毕,希望能提供参考,欢迎支持。
免责声明:本文内容仅供参考,不代表本站观点。转载或引用请注明出处。









