我过去使用过装饰器没有任何问题,但我坚持使用这个。似乎当我的装饰函数被 PyQt 操作调用时,它失败了。我的理论是 PyQt 以某种方式在内部包装了连接的函数并弄乱了签名或类似的东西,但我找不到任何证据。
连接我的意思是这样的:
from PyQt4 import QtGui
# In my widget init...
self.action_my_method = QtGui.QAction("action_my_method", self)
self.action_my_method.triggered.connect(self.my_method)
这是我的简单装饰器:
from functools import wraps
def simple_decorator(fn):
@wraps(fn)
def wrapper(*args, **kwargs):
from inspect import getargspec
print getargspec(fn)
return fn(*args, **kwargs)
return wrapper
当我用它来装饰一个没有任何参数(def my_method(self)
)的方法,并直接从我的 QWidget 类中执行它时,它工作正常。当我使用菜单触发操作时,我得到:
# Traceback (most recent call last):
# File "[...].py", line 88, in wrapper
# return fn(*args, **kwargs)
# TypeError: my_method() takes exactly 1 argument (2 given)
我看到了一个 arg 规范:
ArgSpec(args=['self'], varargs=None, keywords=None, defaults=None)
如果我添加*args
到我的方法中,所以签名是my_method(self, *args)
,装饰器工作正常并且 arg 规范是:
ArgSpec(args=['self'], varargs='args', keywords=None, defaults=None)
我在这里看不到任何线索,因为装饰器在直接调用时可以正常工作,但在被操作触发时会失败。
任何人都可以对此有所了解,或者提供一些我可以用来进一步调试它的东西吗?