诸神缄默不语-个人CSDN博文目录
比较经典的不可靠服务就是访问网络。
最简单的重试策略就是随机time.sleep然后try-catch,这个太基础了我就不写了。本文主要介绍一些比较复杂的策略及其解决方案,比如指数退避及在其基础上衍生出的需求。
最近更新时间:2023.6.2
最早更新时间:2023.6.2
官方GitHub项目:jd/tenacity: Retrying library for Python
官方文档:Tenacity — Tenacity documentation
直接用@retry
装饰访问不可靠服务的函数就可以。
代码示例:
...
from tenacity import (
retry,
stop_after_attempt,
wait_random_exponential,
)
...
@retry(wait=wait_random_exponential(min=60, max=6000), stop=stop_after_attempt(6)) #60和6000都是秒数,OpenAI官方给的是1和60,是为了OpenAI的API接口速率限制,跟我的场景不一样。这个根据实际情况确定就行
def avoid_proxy_die(response_data:str):
response1=requests.post(url='https://api.openai.com/v1/chat/completions',
headers={'Authorization':f"Bearer {API_KEY}",
'content-type':'application/json'},
data=response_data,
proxies={"http":"127.0.0.1:7890","https":"127.0.0.1:7890"}
)
return response1
比较简单的实现方式就是在特定异常上直接增加指定睡眠时间:
@retry(wait=wait_random_exponential(min=20, max=600),stop=stop_after_attempt(6))
def avoid_ChatGPT_die(response_data:str):
try:
response1=requests.post(url='https://api.openai.com/v1/chat/completions',
headers={'Authorization':f"Bearer {API_KEY}",
'content-type':'application/json'},
data=response_data,
proxies={"http":"127.0.0.1:7890","https":"127.0.0.1:7890"}
)
except Exception as e: #这个是代理寄了
time.sleep(60)
raise e
if response1.status_code==200:
return response1
else: #这些情况包括:超过频率限制,秘钥余额用完了,服务器炸了
raise Exception
ChatGPT给了一个更复杂的解决方案,我没有实现过,也列出来以供参考。
大致逻辑是给函数再包一层用@retry
装饰的函数,对不同的异常分别手动调用不同的退避策略:
from tenacity import retry, stop_after_attempt, wait_random_exponential, RetryError
from time import sleep
class SpecifiedException(Exception):
pass
class OtherException(Exception):
pass
@retry(stop=stop_after_attempt(3))
def custom_retry(func):
try:
func()
except SpecifiedException:
sleep(wait_random_exponential(min=1, max=60).next())
raise RetryError
except OtherException:
sleep(wait_random_exponential(min=60, max=6000).next())
raise RetryError
except Exception:
# handle all other exceptions
pass
def my_func():
# your code here
pass
custom_retry(my_func)
略,待补。