Django setUpTestData()与setUp()

rne*_*ius 48 python django unit-testing

Django 1.8附带了一个重构的TestCase,它允许通过setUpTestData()方法使用事务和保存点在类级别进行数据初始化.这与在每个测试方法之前运行的unittest的setUp()形成对比.

问题:Django现在存在的用例是什么?setUp()setUpTestData()

我只是在寻找客观的,高级的答案,否则这个问题对Stack Overflow来说太宽泛了.

小智 41

有一些不能作为类方法运行的设置代码并不罕见.一个值得注意的例子是Django 测试客户端:您可能不希望在跨共享大量相同数据的测试中重用相同的客户端实例,实际上,自动包含在Django的子类中的客户端实例SimpleTestCase按照测试方法创建的,而不是整个班级.假设您使用以下setUp方法从Django 1.8之前的世界进行了测试:

    def setUp(self):
        self.the_user = f.UserFactory.create()
        self.the_post = f.PostFactory.create(author=self.the_user)
        self.client.login(
            username=self.the_user.username, password=TEST_PASSWORD
        )
        # ... &c.

您可能想要通过更改setUp为顶部setUpTestData@classmethod装饰器,并将所有selfs 更改为,来使测试用例现代化cls.但那会失败AttributeError: type object 'MyTestCase' has no attribute 'client'!相反,您应该使用setUpTestData共享数据和setUpper-test-method客户端:

    @classmethod
    def setUpTestData(cls):
        cls.the_user = f.UserFactory.create()
        cls.the_post = f.PostFactory.create(author=cls.the_user)
        # ... &c.

    def setUp(self):
        self.client.login(
            username=self.the_user.username, password=TEST_PASSWORD
        )

注意:如果您想知道变量f在示例代码中做了什么,它来自factoryboy - 一个用于为测试创建对象的有用夹具库.

  • 值得从此方法中添加更多详细信息https://makina-corpus.com/blog/metier/2015/how-to-optimize-django-unit-tests-with-setuptestdata。如果您的测试数据每次测试都会更改,则只要您在`setUp`中执行`self.model.refresh_from_db()`,您仍然可以在`setUpTestData`中创建可变模型。TC的更改将回滚,但是如果没有该手动步骤,则self.model会引用上一次运行的数据。通过setUp步骤,您可以按测试用例进行读取,但是通常这比按测试用例进行写入要快。 (2认同)

小智 14

摘自此测试教程:https://developer.mozilla.org/en-US/docs/Learn/Server-side/Django/Testing#Views

setUpTestData()在测试运行开始时调用一次,用于类级别设置.您可以使用它来创建不会在任何测试方法中修改或更改的对象.

setUp()在每个测试函数之前调用,以设置可能被测试修改的任何对象(每个测试函数都将获得这些对象的"新"版本).


Joa*_*lon 6

缓存问题。即使 Django 在通过事务回滚提供测试隔离方面做得更好,缓存仍然是手动生成和清除的。

[编辑]:SetUpTestData 定义每次测试后数据库将恢复到的状态,并使用仅执行一次的方法来执行此操作,事务回滚由 Django 在幕后完成。这不适用于缓存。如果您希望每次测试的缓存都相同,则需要在每次测试之间重置它,因此需要setUp。Django 可以回滚数据库,但不能回滚所有内容。

(谢谢 bryan-oakley 的建议)

  • 这似乎没有回答所提出的问题。 (2认同)