gpt4 book ai didi

python - Gevent:重试一次greenlet

转载 作者:行者123 更新时间:2023-11-28 18:50:15 25 4
gpt4 key购买 nike

我在 Gevent 池中执行几十个 HTTP 请求。

目标是在请求失败时重试一次,但仅重试一次。否则,它应该抛出异常。

我如何使用 at pool 编写 gevent 代码以支持在失败时重新运行一次 HTTP 请求?

这种方法行得通吗?

import requests
import gevent
from gevent.pool import Pool

pool = Pool(10)

def do_request(id):
r = requests.get('http://example.com/%u' % id)
if not r.status_code == 200:
raise RuntimeError(id)

def spawn_greenlet(id, is_retry=False):
if not is_retry:
g = gevent.spawn(id)
g.link_exception(retry_once)
else:
g = pool.spawn(id)
g.link_exception(raise_exception)
return g

def retry_once(greenlet):
return spawn_greenlet(greenlet.exception.args[0])

def raise_exception(greenlet):
if greenlet.exception:
raise greenlet.exception
raise RuntimeError('Unknown error in greenlet processing.')


greenlets = pool.map(spawn_greenlet, [1, 2, 3, 4, 5])
gevent.joinall(greenlets)
  • 有没有比通过异常参数更简洁的方法来获取 greenlet 函数的参数?
  • 是否有可能 joinall(greenlets) 方法在 do_request 内部发生异常之后但在调用 retry_once 事件处理程序之前返回?
  • 是否有更简洁的方法来使用相同的参数重新启动 greenlet,这样我就不需要 spawn_greenlet 处的 is_retry kwarg?
  • 据我了解,gevent.joinall(greenlets) 仅加入 map 返回的 greenlet。出现异常时,是否将原来的greenlet替换为retry_once返回的新greenlet?如果不是,即使额外的 greenlet 仍在运行,处理是否继续?在这种情况下,我如何才能等待所有 greenlet 完成?

Gevent 文档非常稀缺,网络上似乎没有其他资源对此进行记录,尽管这是一个相当常见的用例。因此,我不认为这是一个过于本地化的问题。

最佳答案

不要使用 spawn/link/link_exception 来重试。只需使用普通的 Python:

def do_something_with_retry(*args):
try:
return do_something(*args)
except Exception:
return do_something(*args)

此外,gevent.pool.Pool.map 会自动在给定的池中生​​成 greenlet,您不必这样做。

pool = Pool(10)
pool.map(do_something_with_retry, [1, 2, 3])

现在,你只需要实现do_something(),可以是普通的Python/requests代码:

def do_something(*args):
return requests.get('http://gevent.org')

玩得开心!

关于python - Gevent:重试一次greenlet,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/13992785/

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