36

タイムアウトにurllib2.request達すると、urllib2.URLError例外が発生します。接続の確立を再試行するpythonicの方法は何ですか?

4

4 に答える 4

65

私は再試行デコレータを使用します。他にもありますが、これはかなりうまくいきます。使用方法は次のとおりです。

@retry(urllib2.URLError, tries=4, delay=3, backoff=2)
def urlopen_with_retry():
    return urllib2.urlopen("http://example.com")

が発生した場合、これは関数を再試行しますURLError。上記のリンクでパラメーターのドキュメントを確認してください。ただし、基本的には最大 4 回再試行し、指数関数的なバックオフ遅延が毎回 2 倍になります (例: 3 秒、6 秒、12 秒)。

于 2012-02-25T18:27:00.550 に答える
9

これに特化したライブラリがいくつかあります。

1つはバックオフで、特に機能的な感覚で設計されています。デコレータには、連続する遅延値を生成するジェネレータを返す任意の callable が渡されます。最大再試行時間が 32 秒の単純な指数バックオフは、次のように定義できます。

@backoff.on_exception(backoff.expo,
                      urllib2.URLError,
                      max_value=32)
def url_open(url):
    return urllib2.urlopen("http://example.com")

もう 1 つは再試行です。これは非常によく似た機能を備えていますが、事前定義されたキーワード引数によって再試行パラメーターが指定される API です。

于 2015-01-31T04:55:10.160 に答える
5

@Karl Barker がコメントで提案したように、タイムアウトを再試行するには、例外をキャッチできます。

assert ntries >= 1
for _ in range(ntries):
    try:
        page = urlopen(request, timeout=timeout)
        break # success
    except URLError as err:
        if not isinstance(err.reason, socket.timeout):
           raise # propagate non-timeout errors
else: # all ntries failed 
    raise err # re-raise the last timeout error
# use page here
于 2012-02-25T18:36:52.240 に答える