我正在使用Python进行一系列单元测试,其中一些测试依赖于配置变量的值。这些变量存储在全局Python配置文件中,并在其他模块中使用。我想为配置变量的不同值编写单元测试,但尚未找到实现此目的的方法。
我没有可能重写我正在测试的方法的签名。
这就是我想要实现的目标:
from my_module import my_function_with_global_var
class TestSomething(self.unittest):
def test_first_case(self):
from config import MY_CONFIG_VARIABLE
MY_CONFIG_VARIABLE = True
self.assertEqual(my_function_with_global_var(), "First result")
def test_second_case(self):
from config import MY_CONFIG_VARIABLE
MY_CONFIG_VARIABLE = False
self.assertEqual(my_function_with_global_var(), "Second result")
感谢。
编辑:使示例代码更明确。
答案 0 :(得分:62)
您可能想要模拟这些全局变量。这样做的好处是,一旦你完成,全局变量就会重置。 Python附带了一个模拟模块,可以让你这样做。
unittest.mock.patch
可用作装饰者:
class TestSomething(self.unittest):
@patch('config.MY_CONFIG_VARIABLE', True)
def test_first_case(self):
self.assertEqual(my_function_with_global_var(), "First result")
您也可以将其用作上下文管理器:
def test_first_case(self):
with patch('config.MY_CONFIG_VARIABLE', True):
self.assertEqual(my_function_with_global_var(), "First result")
答案 1 :(得分:45)
如@Flimm's answer中那样使用unittest.mock.patch
,如果您可以使用的话。
不要这样做:
from my_module import my_function_with_global_var
但是这个:
import my_module
然后您可以将MY_CONFIG_VARIABLE
注入导入的my_module
,而无需更改受测试的系统,如下所示:
class TestSomething(unittest.TestCase): # Fixed that for you!
def test_first_case(self):
my_module.MY_CONFIG_VARIABLE = True
self.assertEqual(my_module.my_function_with_global_var(), "First result")
def test_second_case(self):
my_module.MY_CONFIG_VARIABLE = False
self.assertEqual(my_module.my_function_with_global_var(), "Second result")
我在my answer to How can I simulate input to stdin for pyunit?中做了类似的事情。
答案 2 :(得分:2)
您将MY_CONFIG_VARIABLE
导入到本地作用域中,然后立即使用其他对象覆盖该名称。这不会改变config
模块中的值。尝试
import config
config.MY_CONFIG_VARIABLE = False
代替。