Python3 坚韧重试(w/out 装饰器)在使用 gspread 时给出错误声明 "missing arguments"

Python3 retrying with tenacity (w/out decorators) gives error claiming "missing arguments" when using gspread

我正在尝试使用 tenacity 模块来避免来自 gspread 的频繁请求错误 (APIErrors)。我了解 tenacity 使用装饰器的常见示例,但我想使用 tenacity 的 Retrying() 函数,因此我可以让它重试 gspread 的电子表格单元格更新方法 sheet.update_acell()

出于某种原因,使用 sheet.update_acell() 重试实际上并不 'give' 函数(或其他)的参数。然而,人为设计的多参数示例非常有效。

我的代码(导入和 google API 凭据除外):

# gspread authorization
gs_client = gspread.authorize(creds)
workbook = gs_client.open_by_key(sheet_key)
sheet = workbook.sheet1

ret = tenacity.Retrying(stop=tenacity.stop_after_attempt(30),
                        wait=tenacity.wait_exponential(multiplier=0.5, max=60))

# contrived example
def retry_example(arg0, arg1):
    print(arg0, arg1)
ret.call(retry_example,'foo','bar')  #works perfectly

# gspread example
ret.call(sheet.update_acell(),'A1',1)  #doesn't work, the arguments aren't found

输出:

foo bar
Traceback (most recent call last):
  File "c:/Users/.../tenacitytest.py", line 28, in <module>
    ret.call(sheet.update_acell(),'A1',1)
TypeError: update_acell() missing 2 required positional arguments: 'label' and 'value'

运行 没有坚韧的 gspread 东西可以正常工作,所以我确定我调用 update_acell() 是正确的。

我觉得这可能是因为 gspread 的 update_acell() 是一种方法,不像 example_func()? 任何帮助将不胜感激。

您不应在 Retrying 调用中使用括号。您应该传递如下参数

希望这会奏效 ;)

ret.call(sheet.update_acell,'A1',1)

示例:

from tenacity import Retrying, stop_after_attempt

def foo(arg1, arg2):
    print('Arguments are: {} {}'.format(arg1, arg2))
    raise Exception('Throwing Exception')

def bar(max_attempts=3):
    retryer = Retrying(stop=stop_after_attempt(max_attempts), reraise=True)
    retryer(foo, 'my arg1', 'my arg2')

让我们试试错误场景:

>>> from tenacity import Retrying, stop_after_attempt
>>>
>>> def foo(arg1, arg2):
...     print('Arguments are: {} {}'.format(arg1, arg2))
...     raise Exception('Throwing Exception')
...
>>> def bar(max_attempts=3):
...     retryer = Retrying(stop=stop_after_attempt(max_attempts), reraise=True)
...     retryer(foo(), 'my arg1', 'my arg2')
...
>>> bar()
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "<stdin>", line 3, in bar
TypeError: foo() missing 2 required positional arguments: 'arg1' and 'arg2'
>>>