Tôi đang sử dụng thư viện Yêu cầu tuyệt vời trong tập lệnh Python của mình:
import requests
r = requests.get("some-site.com")
print r.text
Tôi muốn sử dụng proxy vớ. Nhưng yêu cầu hiện chỉ hỗ trợ proxy HTTP.
Làm thế nào tôi có thể làm điều đó?
Câu trả lời:
Cách hiện đại:
pip install -U requests[socks]
sau đó
import requests
resp = requests.get('http://go.to',
proxies=dict(http='socks5://user:pass@host:port',
https='socks5://user:pass@host:port'))
bash -c "pip install -U requests[socks]"
thay thế nếu không zsh sẽ phàn nàn zsh: no matches found: requests[socks]
.
pip install 'requests[socks]'
sẽ là đủ
pip install -U requests[socks]
là enogh
requests
lên phiên bản hỗ trợ SOCKS (> 2.10.0), hãy chạy pip: pip install requests==2.18.4
(2.18.4 tại thời điểm viết bài này), nhưng hãy kiểm tra: pypi. python.org/pypi/requests cho phiên bản mới nhất (trang này sẽ hiển thị cho bạn ở tiêu đề trên cùng phiên bản ổn định mới nhất là gì).
socks
xung đột tên mô-đun với qBittorrent
, tôi cần xóa / di chuyển ~/.local/share/data/qBittorrent/nova3/socks.py
và loại bỏ điều đó socks.pyc
, để giải quyết thông báo lỗi module 'socks' has no attribute 'create_connection'
và bad magic number in 'socks':
tương ứng.
Trong trường hợp ai đó đã thử tất cả các câu trả lời cũ hơn này và vẫn gặp sự cố như:
requests.exceptions.ConnectionError:
SOCKSHTTPConnectionPool(host='myhost', port=80):
Max retries exceeded with url: /my/path
(Caused by NewConnectionError('<requests.packages.urllib3.contrib.socks.SOCKSConnection object at 0x106812bd0>:
Failed to establish a new connection:
[Errno 8] nodename nor servname provided, or not known',))
Có thể do, theo mặc định, requests
được định cấu hình để giải quyết các truy vấn DNS ở phía cục bộ của kết nối.
Hãy thử thay đổi URL proxy của bạn từ socks5://proxyhost:1234
thành socks5h://proxyhost:1234
. Lưu ý thêm h
(nó là viết tắt của độ phân giải tên máy chủ).
Mặc định của mô-đun gói PySocks là thực hiện giải quyết từ xa và tôi không chắc tại sao các yêu cầu lại thực hiện tích hợp của chúng hoàn toàn khác nhau, nhưng chúng tôi ở đây.
socks5h
cách tiếp cận là rất nhiều bụi hơn workaround khỉ vá Tôi đã lo lắng tôi sẽ phải làm trước.
socks5h://
tài liệu Python về proxy ở bất kỳ đâu. Chắc là đã nhìn nhầm chỗ. Gotta tình yêu SO.
Bạn cần cài đặt pysocks , phiên bản của tôi là 1.0 và mã phù hợp với tôi:
import socket
import socks
import requests
ip='localhost' # change your proxy's ip
port = 0000 # change your proxy's port
socks.setdefaultproxy(socks.PROXY_TYPE_SOCKS5, ip, port)
socket.socket = socks.socksocket
url = u'http://ajax.googleapis.com/ajax/services/search/images?v=1.0&q=inurl%E8%A2%8B'
print(requests.get(url).text)
Ngay sau khi python requests
sẽ được hợp nhất với SOCKS5
pull request, nó sẽ thực hiện đơn giản như sử dụng proxies
từ điển:
#proxy
# SOCKS5 proxy for HTTP/HTTPS
proxies = {
'http' : "socks5://myproxy:9191",
'https' : "socks5://myproxy:9191"
}
#headers
headers = {
}
url='http://icanhazip.com/'
res = requests.get(url, headers=headers, proxies=proxies)
Một tùy chọn khác, trong trường hợp bạn không thể chờ request
sẵn sàng, khi bạn không thể sử dụng requesocks
- như trên GoogleAppEngine do thiếu pwd
mô-đun tích hợp, là sử dụng PySocks đã được đề cập ở trên:
socks.py
tệp từ repo và đặt một bản sao vào thư mục gốc của bạn;import socks
vàimport socket
Tại thời điểm này, hãy cấu hình và liên kết socket trước khi sử dụng với urllib2
- trong ví dụ sau:
import urllib2
import socket
import socks
socks.set_default_proxy(socks.SOCKS5, "myprivateproxy.net",port=9050)
socket.socket = socks.socksocket
res=urllib2.urlopen(url).read()
# SOCKS5 proxy for HTTP/HTTPS
proxiesDict = {
'http' : "socks5://1.2.3.4:1080",
'https' : "socks5://1.2.3.4:1080"
}
# SOCKS4 proxy for HTTP/HTTPS
proxiesDict = {
'http' : "socks4://1.2.3.4:1080",
'https' : "socks4://1.2.3.4:1080"
}
# HTTP proxy for HTTP/HTTPS
proxiesDict = {
'http' : "1.2.3.4:1080",
'https' : "1.2.3.4:1080"
}
requesocks
?
proxies
từ điển cho requests
yêu cầu kéo mới nhất , mà tại thời điểm này chưa được hợp nhất. @see - github.com/kennethreitz/requests/pull/2953
Tôi đã cài đặt pysocks và con khỉ đã vá create_connection trong urllib3, như thế này:
import socks
import socket
socks.setdefaultproxy(socks.PROXY_TYPE_SOCKS4, "127.0.0.1", 1080)
def create_connection(address, timeout=socket._GLOBAL_DEFAULT_TIMEOUT,
source_address=None, socket_options=None):
"""Connect to *address* and return the socket object.
Convenience function. Connect to *address* (a 2-tuple ``(host,
port)``) and return the socket object. Passing the optional
*timeout* parameter will set the timeout on the socket instance
before attempting to connect. If no *timeout* is supplied, the
global default timeout setting returned by :func:`getdefaulttimeout`
is used. If *source_address* is set it must be a tuple of (host, port)
for the socket to bind as a source address before making the connection.
An host of '' or port 0 tells the OS to use the default.
"""
host, port = address
if host.startswith('['):
host = host.strip('[]')
err = None
for res in socket.getaddrinfo(host, port, 0, socket.SOCK_STREAM):
af, socktype, proto, canonname, sa = res
sock = None
try:
sock = socks.socksocket(af, socktype, proto)
# If provided, set socket level options before connecting.
# This is the only addition urllib3 makes to this function.
urllib3.util.connection._set_socket_options(sock, socket_options)
if timeout is not socket._GLOBAL_DEFAULT_TIMEOUT:
sock.settimeout(timeout)
if source_address:
sock.bind(source_address)
sock.connect(sa)
return sock
except socket.error as e:
err = e
if sock is not None:
sock.close()
sock = None
if err is not None:
raise err
raise socket.error("getaddrinfo returns an empty list")
# monkeypatch
urllib3.util.connection.create_connection = create_connection
Có thể điều này có thể giúp:
Tôi có thể làm điều này trên Linux.
$ pip3 install --user 'requests[socks]'
$ https_proxy=socks5://<hostname or ip>:<port> python3 -c \
> 'import requests;print(requests.get("https://httpbin.org/ip").text)'