gpt4 book ai didi

Python urllib2 强制 IPv4

转载 作者:太空狗 更新时间:2023-10-30 00:33:02 24 4
gpt4 key购买 nike

我正在使用 python 运行脚本,该脚本使用 urllib2 从天气 api 获取数据并将其显示在屏幕上。我遇到的问题是,当我查询服务器时,出现“没有与主机名关联的地址”错误。我可以用网络浏览器查看 api 的输出,我可以用 wget 下载文件,但我必须强制 IPv4 才能让它工作。使用 urllib2.urlopen 时是否可以在 urllib2 中强制使用 IPv4?

最佳答案

不直接,不。

那么,你能做什么?


一种可能是自己将主机名显式解析为 IPv4,然后使用 IPv4 地址而不是名称作为主机。例如:

host = socket.gethostbyname('example.com')
page = urllib2.urlopen('http://{}/path'.format(host))

但是,某些虚拟服务器站点可能需要 Host: example.com header ,而它们将取而代之的是 Host: 93.184.216.119。您可以通过覆盖 header 来解决此问题:

host = socket.gethostbyname('example.com')
request = urllib2.Request('http://{}/path'.format(host),
headers = {'Host': 'example.com'})
page = urllib2.urlopen(request)

或者,您可以提供自己的处理程序来代替标准处理程序。但标准处理程序大多只是 httplib.HTTPConnection 的包装器,真正的问题在于 HTTPConnection.connect

因此,干净的方法是创建您自己的 httplib.HTTPConnection 子类,它会像这样覆盖 connect:

def connect(self):
host = socket.gethostbyname(self.host)
self.sock = socket.create_connection((host, self.post),
self.timeout, self.source_address)
if self._tunnel_host:
self._tunnel()

然后创建您自己的 urllib2.HTTPHandler 子类,覆盖 http_open 以使用您的子类:

def http_open(self, req):
return self.do_open(my wrapper.MyHTTPConnection, req)

……对于 HTTPSHandler 也是类似的,然后按照 urllib2 文档中所示正确连接所有内容。

做同样事情的快速而肮脏的方法是将 httplib.HTTPConnection.connect monkeypatch 到上面的函数。


最后,您可以使用不同的库来代替 urllib2。根据我的内存,requests 并没有使这变得更容易(最终,您必须重写或 monkeypatch 稍微不同的方法,但它实际上是相同的)。但是,任何 libcurl 包装器都允许您执行与 curl_easy_setopt(h, CURLOPT_IPRESOLVE, CURLOPT_IPRESOLVE_V4) 相同的操作。

关于Python urllib2 强制 IPv4,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/18007174/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com