Skip to main content
 首页 » 编程设计

python之使用 Tor 代理时的多线程爬虫

2025年01月19日34lidabo

我正在尝试构建使用 Tor 代理的多线程爬虫: 我正在使用以下建立 tor 连接:

from stem import Signal 
from stem.control import Controller 
controller = Controller.from_port(port=9151) 
def connectTor(): 
    socks.setdefaultproxy(socks.PROXY_TYPE_SOCKS5, "127.0.0.1", 9150) 
    socket.socket = socks.socksocket 
 
 
def renew_tor(): 
    global request_headers 
    request_headers = { 
        "Accept-Language": "en-US,en;q=0.5", 
        "User-Agent": random.choice(BROWSERS), 
        "Accept": "text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8", 
        "Referer": "http://thewebsite2.com", 
        "Connection": "close" 
    } 
 
    controller.authenticate() 
    controller.signal(Signal.NEWNYM) 

这是 url getter :

def get_soup(url): 
    while True: 
        try: 
            connectTor() 
            r = requests.Session() 
            response = r.get(url, headers=request_headers) 
            the_page = response.content.decode('utf-8',errors='ignore') 
            the_soup = BeautifulSoup(the_page, 'html.parser') 
            if "captcha" in the_page.lower(): 
                print("flag condition matched while url: ", url) 
                #print(the_page) 
                renew_tor() 
            else: 
                return the_soup 
                break 
        except Exception as e: 
            print ("Error while URL :", url, str(e)) 

然后我正在创建多线程获取作业:

with futures.ThreadPoolExecutor(200) as executor: 
            for url in zurls: 
                future = executor.submit(fetchjob,url) 

然后我收到以下错误,我在使用多处理时没有看到:

 Socket connection failed (Socket error: 0x01: General SOCKS server failure) 

我将不胜感激任何避免 socks 错误和提高爬行方法性能以使其成为多线程的建议。

请您参考如下方法:

这是为什么猴子修补 socket.socket 不好的一个完美例子。

这用 SOCKS 套接字替换了 所有 socket 连接(几乎所有东西)使用的套接字。

当您稍后连接到 Controller 时,它会尝试使用 SOCKS 协议(protocol)进行通信,而不是建立直接连接。

因为您已经在使用requests,所以我建议摆脱 SocksiPy 和 socks.socket = socks.socksocket 代码并使用 SOCKS proxy内置于请求中的功能:

proxies = { 
    'http': 'socks5h://127.0.0.1:9050', 
    'https': 'socks5h://127.0.0.1:9050' 
} 
 
response = r.get(url, headers=request_headers, proxies=proxies)