通过装饰器注入类属性

问题描述 投票:1回答:1

我有一大堆Django TestCases使用setUp方法来初始化一些在大量测试中使用的属性,它们的构造方式和相互依赖的逻辑我想要移出测试用例并重用

def setUp(self):
    self.property_1 = ##some logic
    ...

我想将这些重写为一些便利包装器,可以通过简单的继承或装饰器注入到类中,例如:

@with_property_1(x=1, y=2)
def setUp(self):
    ...


def with_property_1(**model_kwargs):
    def wrapper(f):
        def wrapped(*args, **kwargs):
            self = args[0]
            self.property_1 = ## logic
            f(*args, **kwargs)
        return wrapped
    return wrapper

但问题是PyCharm没有认识到那些实例属性存在,因为TestCase类中的任何内容都没有设置它们。有没有另一种方法我可以很好地实现这一点,或者一种方法来哄骗PyCharm识别这些属性是合法的,因为装饰器的存在?

python django pycharm decorator testcase
1个回答
0
投票

免责声明:这是未经测试的。

这里的问题是Python不能只是奇怪地将self放入装饰器中的上下文中(这在任何IDE中都不起作用)。您可能忘记的是,当您调用它时,self是传递给每个类方法的参数之一。因此,它存在于你的*args中,你可以操纵它。

这是我的试用代码:

def with_property_1(**model_kwargs):
  def wrapper(f):
    def wrapped(*args, **kwargs):
      for key, value in model_kwargs.items():
        setattr(args[0], key, value)
      f(*args, **kwargs)
    return wrapped
  return wrapper

说明:

  1. 迭代**model_kwargs中的每个键/值。
  2. 使用args[0]修改self,它应该是setattr变量,使用提供的kwargs。
  3. 使用更新的self变量正常调用函数。
© www.soinside.com 2019 - 2024. All rights reserved.