如何通过Tor在Python中使用urllib2发送请求?

55 投票
12 回答
48738 浏览
提问于 2025-04-15 12:45

我正在尝试用Python写一个爬虫来抓取网站。我想把Tor和Python结合起来,也就是说,我想通过Tor匿名地抓取网站。

我试过这样做,但好像不太成功。我检查了一下我的IP地址,发现它和我使用Tor之前的地址还是一样的。我是通过Python来检查的。

import urllib2
proxy_handler = urllib2.ProxyHandler({"tcp":"http://127.0.0.1:9050"})
opener = urllib2.build_opener(proxy_handler)
urllib2.install_opener(opener)

12 个回答

3

以下代码在Python 3.4上是完全可用的。

(使用这段代码时,你需要保持TOR浏览器打开)

这个脚本通过socks5连接到TOR,获取来自checkip.dyn.com的IP地址,改变身份后重新发送请求以获取新的IP(循环10次)

你需要安装合适的库才能让它正常工作。(好好享受,但不要滥用)

import socks
import socket
import time
from stem.control import Controller
from stem import Signal
import requests
from bs4 import BeautifulSoup
err = 0
counter = 0
url = "checkip.dyn.com"
with Controller.from_port(port = 9151) as controller:
    try:
        controller.authenticate()
        socks.setdefaultproxy(socks.PROXY_TYPE_SOCKS5, "127.0.0.1", 9150)
        socket.socket = socks.socksocket
        while counter < 10:
            r = requests.get("http://checkip.dyn.com")
            soup = BeautifulSoup(r.content)
            print(soup.find("body").text)
            counter = counter + 1
            #wait till next identity will be available
            controller.signal(Signal.NEWNYM)
            time.sleep(controller.get_newnym_wait())
    except requests.HTTPError:
        print("Could not reach URL")
        err = err + 1
print("Used " + str(counter) + " IPs and got " + str(err) + " errors")
9
pip install PySocks

然后:

import socket
import socks
import urllib2

ipcheck_url = 'http://checkip.amazonaws.com/'

# Actual IP.
print(urllib2.urlopen(ipcheck_url).read())

# Tor IP.
socks.setdefaultproxy(socks.PROXY_TYPE_SOCKS5, '127.0.0.1', 9050)
socket.socket = socks.socksocket
print(urllib2.urlopen(ipcheck_url).read())

仅使用 urllib2.ProxyHandler,就像在 这个链接 中提到的那样,会失败,出现以下问题:

Tor is not an HTTP Proxy

提到的问题在这里: 我该如何在 urllib2 中使用 SOCKS 4/5 代理?

在 Ubuntu 15.10、Tor 0.2.6.10 和 Python 2.7.10 上测试过。

23

你正在尝试连接一个SOCKS端口,但Tor会拒绝任何非SOCKS的流量。你可以通过一个中间人——Privoxy,使用8118端口进行连接。

举个例子:

proxy_support = urllib2.ProxyHandler({"http" : "127.0.0.1:8118"})
opener = urllib2.build_opener(proxy_support) 
opener.addheaders = [('User-agent', 'Mozilla/5.0')]
print opener.open('http://www.google.com').read()

另外,请注意传递给ProxyHandler的属性,不要在ip:port前加http前缀。

撰写回答