【问题标题】:django testcase with --keepdb is not resetting object ids between tests带有 --keepdb 的 django 测试用例不会在测试之间重置对象 ID
【发布时间】:2020-09-04 13:22:35
【问题描述】:

最近我将使用 Python 2.7 和 Django 1.11 制作的 django 应用程序更新为 Python 3 和 Django 3.1。

我有几个使用 django.test.TestCase 的测试用例。其中一些测试是假设数据库将在测试执行之间完全重置,除其他外,预计模型的最后一个 id 也会被重置,例如,如果我在测试中创建一个对象并且将其保存到数据库中,对象将始终从 1 开始接收相同的 id。

这在 Django 1.11 上的行为与此完全相同,我能够使用 --keepdb 标志来避免每次都重新创建数据库。

但是,在我升级到 Python 3 和 Django 3.1 之后,我注意到情况不再如此。我注意到在测试执行后所有对象都从数据库中删除,但是在下一次测试执行中,新对象是从上次使用的 pk 开始使用 pk 创建的,所以我不能再指望创建的对象将具有可预测的PK。这会导致一个非常烦人的行为,如果我在重新创建数据库后运行测试,测试将通过,但如果我再次运行测试,保持数据库,它将不会通过,因为 pks 会有所不同。

如果我在运行测试时删除 --keepdb 标志,则 pk 会全部重置,但这会使测试执行速度变慢,因为我的数据库结构需要几分钟才能创建。

是否有一个选项可以在每次测试执行时重置 pks?在 1.11 之后的版本中,Django 上的这种行为实际上是否发生了变化?

【问题讨论】:

    标签: python django testing


    【解决方案1】:

    我在 StackOverflow 上找到了我的问题的答案: Can Django flush its database(s) between every unit test?

    建议设置:

    reset_sequences = True
    

    关于测试类。

    documentation for reset_sequences 上有一个警告,但是:

    Unless you are explicitly testing primary keys sequence numbers, it is
    recommended that you do not hard code primary key values in tests.
    

    还有:

    Using reset_sequences = True will slow down the test, since the primary key
    reset is an relatively expensive database operation.
    

    【讨论】:

    • 非常感谢!我在表现方面遇到了同样的麻烦。在我的 environment.py 中,我使用 django.test.TestCase 的实例创建了一个 context.test_case。使用此设置,我遇到了与您相同的问题,我通过创建 django.test.TransactionTestCase 的子类并将 reset_sequences = True 添加到该类中,使用您的方法解决了这个问题。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-06-10
    • 2018-12-21
    • 1970-01-01
    • 1970-01-01
    • 2014-11-09
    相关资源
    最近更新 更多