请求中的 URL 已超出最大重试次数
- 2025-01-03 08:41:00
- admin 原创
- 120
问题描述:
我正在尝试获取App Store > Business的内容:
import requests
from lxml import html
page = requests.get("https://itunes.apple.com/in/genre/ios-business/id6000?mt=8")
tree = html.fromstring(page.text)
flist = []
plist = []
for i in range(0, 100):
app = tree.xpath("//div[@class='column first']/ul/li/a/@href")
ap = app[0]
page1 = requests.get(ap)
当我尝试range
使用时(0,2)
,它可以工作,但是当我输入时range
,100
它显示此错误:
Traceback (most recent call last):
File "/home/preetham/Desktop/eg.py", line 17, in <module>
page1 = requests.get(ap)
File "/usr/local/lib/python2.7/dist-packages/requests/api.py", line 55, in get
return request('get', url, **kwargs)
File "/usr/local/lib/python2.7/dist-packages/requests/api.py", line 44, in request
return session.request(method=method, url=url, **kwargs)
File "/usr/local/lib/python2.7/dist-packages/requests/sessions.py", line 383, in request
resp = self.send(prep, **send_kwargs)
File "/usr/local/lib/python2.7/dist-packages/requests/sessions.py", line 486, in send
r = adapter.send(request, **kwargs)
File "/usr/local/lib/python2.7/dist-packages/requests/adapters.py", line 378, in send
raise ConnectionError(e)
requests.exceptions.ConnectionError: HTTPSConnectionPool(host='itunes.apple.com', port=443): Max retries exceeded with url: /in/app/adobe-reader/id469337564?mt=8 (Caused by <class 'socket.gaierror'>: [Errno -2] Name or service not known)
解决方案 1:
只需使用requests
以下功能:
import requests
from requests.adapters import HTTPAdapter
from urllib3.util.retry import Retry
session = requests.Session()
retry = Retry(connect=3, backoff_factor=0.5)
adapter = HTTPAdapter(max_retries=retry)
session.mount('http://', adapter)
session.mount('https://', adapter)
session.get(url)
这将是GET
URL 并在出现的情况下重试 3 次requests.exceptions.ConnectionError
。backoff_factor
将有助于在尝试之间应用延迟,以避免在定期请求配额的情况下再次失败。
看一下urllib3.util.retry.Retry
,它有许多选项可以简化重试。
解决方案 2:
这里发生的情况是iTunes服务器拒绝您的连接(您在短时间内从同一 IP 地址发送了太多请求)
使用 URL 时超出最大重试次数:/in/app/adobe-reader/id469337564?mt=8
错误跟踪具有误导性,它应该是类似“无法建立连接,因为目标机器主动拒绝”。
Github 上有一个关于 python.requests lib 的问题,请点击此处查看
为了解决这个问题(不是一个大问题,而是一个误导性的调试跟踪),你应该捕获与连接相关的异常,如下所示:
try:
page1 = requests.get(ap)
except requests.exceptions.ConnectionError:
r.status_code = "Connection refused"
解决这个问题的另一种方法是如果你使用足够的时间间隔向服务器发送请求,这可以通过sleep(timeinsec)
python 中的函数实现(不要忘记导入睡眠)
from time import sleep
总而言之,请求是一个很棒的 python 库,希望能够解决您的问题。
解决方案 3:
就这么做吧,
将以下代码粘贴到page = requests.get(url)
:
import time
page = ''
while page == '':
try:
page = requests.get(url)
break
except:
print("Connection refused by the server..")
print("Let me sleep for 5 seconds")
print("ZZzzzz...")
time.sleep(5)
print("Was a nice sleep, now let me continue...")
continue
不客气 :)
解决方案 4:
我遇到了类似的问题,但以下代码对我有用。
url = <some REST url>
page = requests.get(url, verify=False)
“verify=False”禁用SSL验证。可以照常添加Try和catch。
解决方案 5:
pip install pyopenssl
似乎为我解决了这个问题。
https://github.com/requests/requests/issues/4246
解决方案 6:
在公司环境中指定代理为我解决了这个问题。
page = requests.get("http://www.google.com:80", proxies={"http": "http://111.233.225.166:1234"})
完整错误如下:
request.exceptions.ConnectionError: HTTPSConnectionPool(host='www.google.com', port=80): 使用 url 时超出最大重试次数:/(由 NewConnectionError(': 无法建立新连接:[WinError 10060] 连接尝试失败,因为连接方在一段时间后未正确响应,或者建立连接失败,因为连接的主机未能响应'))
解决方案 7:
实现异常处理总是好的。它不仅有助于避免脚本意外退出,还可以帮助记录错误和信息通知。当使用 Python 请求时,我更喜欢捕获这样的异常:
try:
res = requests.get(adress,timeout=30)
except requests.ConnectionError as e:
print("OOPS!! Connection Error. Make sure you are connected to Internet. Technical Details given below.
")
print(str(e))
renewIPadress()
continue
except requests.Timeout as e:
print("OOPS!! Timeout Error")
print(str(e))
renewIPadress()
continue
except requests.RequestException as e:
print("OOPS!! General Error")
print(str(e))
renewIPadress()
continue
except KeyboardInterrupt:
print("Someone closed the program")
此处 renewIPadress() 是用户定义函数,如果 IP 地址被阻止,它可以更改 IP 地址。您可以不使用此功能。
解决方案 8:
为那些将来遇到这种情况的人添加我自己的经验。我的具体错误是
Failed to establish a new connection: [Errno 8] nodename nor servname provided, or not known'
事实证明,这实际上是因为我的系统上打开文件数已达到上限。这与连接失败或 DNS 错误无关。
解决方案 9:
当我编写 selenium 浏览器测试脚本时,driver.quit()
在使用 JS api 调用之前调用时遇到了此错误。请记住,退出 webdriver 是最后要做的事情!
解决方案 10:
即使在安装了 pyopenssl 并尝试了各种 python 版本后,我还是无法让它在 windows 上运行(而在 mac 上运行良好),所以我切换到 urllib,它可以在 python 3.6(来自 python .org)和 3.7(anaconda)上运行
import urllib
from urllib.request import urlopen
html = urlopen("http://pythonscraping.com/pages/page1.html")
contents = html.read()
print(contents)
解决方案 11:
只需import time
添加:
time.sleep(6)
在 for 循环中的某个地方,避免在短时间内向服务器发送太多请求。数字 6 表示:6 秒。从 1 开始不断测试数字,直到达到有助于避免问题的最少秒数。
解决方案 12:
也可能是网络配置问题。因此,您需要重新配置您的网络配置。
对于 Ubuntu : sudo vim /etc/network/interfaces
在dns-nameserver中添加8.8.8.8并保存。
重置网络:/etc/init.d/networking restart
现在尝试..
解决方案 13:
就我而言,我在 Python 脚本中部署了一些 Docker 容器,然后调用其中一个已部署的服务。当我在调用服务之前添加一些延迟时,错误已修复。我认为它需要时间来准备接受连接。
from time import sleep
#deploy containers
#get URL of the container
sleep(5)
response = requests.get(url,verify=False)
print(response.json())
解决方案 14:
添加我自己的经验:
r = requests.get(download_url)
当我尝试下载 url 中指定的文件时。
错误是
HTTPSConnectionPool(host, port=443): Max retries exceeded with url (Caused by SSLError(SSLError("bad handshake: Error([('SSL routines', 'tls_process_server_certificate', 'certificate verify failed')])")))
我通过添加verify = False
如下函数来更正它:
r = requests.get(download_url + filename)
open(filename, 'wb').write(r.content)
解决方案 15:
检查您的网络连接。我遇到过这种情况,虚拟机没有正确的网络连接。
解决方案 16:
/
我在浏览器中运行路由时遇到了同样的错误,但在 Postman 中,它运行正常。我的问题是,在查询字符串之前没有路由之后的内容。
127.0.0.1:5000/api/v1/search/?location=Madina
在我完成工作/
后提出错误并将其删除。search
解决方案 17:
当您向 的公共 IP 地址发送过多请求时,就会发生这种情况https://itunes.apple.com
。如您所见,这是由于某些原因导致不允许/阻止访问 的公共 IP 地址映射https://itunes.apple.com
。一个更好的解决方案是以下 python 脚本,它可以计算任何域的公共 IP 地址并创建到 /etc/hosts 文件的映射。
import re
import socket
import subprocess
from typing import Tuple
ENDPOINT = 'https://anydomainname.example.com/'
ENDPOINT = 'https://itunes.apple.com/'
def get_public_ip() -> Tuple[str, str, str]:
"""
Command to get public_ip address of host machine and endpoint domain
Returns
-------
my_public_ip : str
Ip address string of host machine.
end_point_ip_address : str
Ip address of endpoint domain host.
end_point_domain : str
domain name of endpoint.
"""
# bash_command = """host myip.opendns.com resolver1.opendns.com | \n # grep "myip.opendns.com has" | awk '{print $4}'"""
# bash_command = """curl ifconfig.co"""
# bash_command = """curl ifconfig.me"""
bash_command = """ curl icanhazip.com"""
my_public_ip = subprocess.getoutput(bash_command)
my_public_ip = re.compile("[0-9.]{4,}").findall(my_public_ip)[0]
end_point_domain = (
ENDPOINT.replace("https://", "")
.replace("http://", "")
.replace("/", "")
)
end_point_ip_address = socket.gethostbyname(end_point_domain)
return my_public_ip, end_point_ip_address, end_point_domain
def set_etc_host(ip_address: str, domain: str) -> str:
"""
A function to write mapping of ip_address and domain name in /etc/hosts.
Ref: https://stackoverflow.com/questions/38302867/how-to-update-etc-hosts-file-in-docker-image-during-docker-build
Parameters
----------
ip_address : str
IP address of the domain.
domain : str
domain name of endpoint.
Returns
-------
str
Message to identify success or failure of the operation.
"""
bash_command = """echo "{} {}" >> /etc/hosts""".format(ip_address, domain)
output = subprocess.getoutput(bash_command)
return output
if __name__ == "__main__":
my_public_ip, end_point_ip_address, end_point_domain = get_public_ip()
output = set_etc_host(ip_address=end_point_ip_address, domain=end_point_domain)
print("My public IP address:", my_public_ip)
print("ENDPOINT public IP address:", end_point_ip_address)
print("ENDPOINT Domain Name:", end_point_domain )
print("Command output:", output)
您可以在运行所需功能之前调用上述脚本:)
解决方案 18:
我的情况比较特殊,上面的答案我都试过了,都没有用。我突然想到是不是跟我的网络代理有关?你知道,我在中国大陆,没有网络代理的话,我无法访问像 google 这样的网站。后来我关掉了网络代理,问题就解决了。
解决方案 19:
为此请求添加标头。
headers={
'Referer': 'https://itunes.apple.com',
'User-Agent': 'Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_0) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/75.0.3770.142 Safari/537.36'
}
requests.get(ap, headers=headers)