【问题标题】:Setting up environment for testing in Python在 Python 中设置测试环境
【发布时间】:2015-08-09 05:47:04
【问题描述】:

我正在使用 Python 中的普通 unittest (import unittest) 编写集成测试,并正在为一些外部服务创建存根。现在我想用一个真实的实现来运行相同的测试;还要保留存根。这样我就可以在有和没有存根的情况下运行测试并比较行为。

我正在通过 SetupTools 和 PyCharm 运行我的测试。我是否有一些通用的方法来设置/注入/引导一个参数,告诉我的代码是使用存根还是真正的实现?命令行优先。任何指针表示赞赏。 :)

【问题讨论】:

  • 单元测试不应该使用真正的实现。如果他们这样做,他们将是集成测试。进行使用真实实现的单独测试。
  • 我只是在使用 unittest 库,但你是对的,它们是集成测试。无论如何:我希望能够同时练习真正的实现和存根。当外部发生变化时,这种比较给了我很多价值。
  • 假设您正在测试一个名为 foo 的单元。本单元使用bar的真实实现。 Bar 有错字并引发错误。即使foo 单元没有任何错误,您对foo 的单元测试也会失败。这就是为什么在单元测试中使用真正的实现是不可取的,我认为你应该重新考虑这种方法。
  • 就像我说的:它们是集成测试。我也有单元测试。我想同时运行两者,而不仅仅是其中一个。但我需要一些方法来管理在那个特定时间点处于活动状态。

标签: python unit-testing integration-testing python-unittest stubbing


【解决方案1】:

听起来您正在寻找mocking framework。模拟框架允许您在测试中为该方法创建一个“存根”。这很好,因为您不想将任何特定于测试的代码插入到实际代码中。

python 2.* 中比较流行的一个模拟框架是python-mock(实际上它是 python 3 自带的)所以你可以把代码写成:

from mock import MagicMock

test_foo_mocked():
    bar = MagicMock()
    bar.return_value = 'fake_val'
    assertEqual(bar(), 'fake_val')

test_foo_real():
    assertEqual(bar(), 'real_val')

旁注:
我真的建议您将这些视为完全不相关的测试。将集成测试与单元测试分开有很多好处。将它们视为运行“相同测试”的两种不同方式可能会鼓励您编写糟糕的测试。单元测试应该能够测试通过集成测试难以或不可能测试的东西,反之亦然。

【讨论】:

  • 感谢您的指点,但我尽量远离 Mocking。虽然我确实有存根,但它确实不需要 Python 中的框架。虽然我可以看到您可能会通过将它们视为一个来完成一些丑陋的测试,但当某些事情发生变化时,您还必须更新几个测试。因此,您最终可能会遇到一种情况,即更新了 real-impl 测试,而 stub-test 正在针对实际 impl 中没有发生的东西运行。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2021-05-12
  • 2012-10-27
  • 2015-09-20
  • 1970-01-01
  • 1970-01-01
  • 2013-01-09
  • 1970-01-01
相关资源
最近更新 更多