如何在 for 循环中动态模拟 python 函数的结果?
How to dynamically mock the result of a python function inside a for loop?
我正在尝试实施一些单元测试来验证包含 for 循环的方法。此方法接收项目列表,并针对其中的每个项目执行函数 foo()
,并将该项目作为参数。
有谁知道如何模拟 foo()
函数以根据作为输入提供的元素动态提供模拟的返回值?
方法:
def foo(i):
if i == 'this':
return 'a'
else:
return 'b'
def bar(items):
results = []
for item in items:
results.append(foo(item))
return results
单元测试:
from unittest import TestCase
from mock import patch
class TestCaseBar(TestCase):
@patch('my_module.foo')
def test_bar(self, mock_foo):
mock_foo.return_value = 'dummy' # I would like to dinamically mock this.
items = ['this', 'that']
result = bar(items)
self.assertEqual(result, ['a', 'b'])
self.assertTrue(mock_foo.call_count, 2)
提前感谢您的回答。
您可以使用为模拟对象的 side_effect
属性 分配一个函数。然后,你可以为它实现模拟细节。
A function to be called whenever the Mock is called. See the side_effect attribute. Useful for raising exceptions or dynamically changing return values.
例如
my_module_64443736.py
:
def foo(i):
if i == 'this':
return 'a'
else:
return 'b'
def bar(items):
results = []
for item in items:
results.append(foo(item))
return results
test_my_module_64443736.py
:
from unittest import TestCase, main
from unittest.mock import patch
from my_module_64443736 import bar
class TestCaseBar(TestCase):
@patch('my_module_64443736.foo')
def test_bar(self, mock_foo):
def dynamicMock(i):
if i == 'this':
return 'teresa teng'
else:
return 'best singer'
mock_foo.side_effect = dynamicMock
items = ['this', 'that']
result = bar(items)
self.assertEqual(result, ['teresa teng', 'best singer'])
self.assertTrue(mock_foo.call_count, 2)
if __name__ == '__main__':
main()
单元测试结果:
.
----------------------------------------------------------------------
Ran 1 test in 0.000s
OK
Name Stmts Miss Cover Missing
-------------------------------------------------------------------------------------
src/Whosebug/64443736/my_module_64443736.py 9 3 67% 2-5
src/Whosebug/64443736/test_my_module_64443736.py 16 0 100%
-------------------------------------------------------------------------------------
TOTAL 25 3 88%
我正在尝试实施一些单元测试来验证包含 for 循环的方法。此方法接收项目列表,并针对其中的每个项目执行函数 foo()
,并将该项目作为参数。
有谁知道如何模拟 foo()
函数以根据作为输入提供的元素动态提供模拟的返回值?
方法:
def foo(i):
if i == 'this':
return 'a'
else:
return 'b'
def bar(items):
results = []
for item in items:
results.append(foo(item))
return results
单元测试:
from unittest import TestCase
from mock import patch
class TestCaseBar(TestCase):
@patch('my_module.foo')
def test_bar(self, mock_foo):
mock_foo.return_value = 'dummy' # I would like to dinamically mock this.
items = ['this', 'that']
result = bar(items)
self.assertEqual(result, ['a', 'b'])
self.assertTrue(mock_foo.call_count, 2)
提前感谢您的回答。
您可以使用为模拟对象的 side_effect
属性 分配一个函数。然后,你可以为它实现模拟细节。
A function to be called whenever the Mock is called. See the side_effect attribute. Useful for raising exceptions or dynamically changing return values.
例如
my_module_64443736.py
:
def foo(i):
if i == 'this':
return 'a'
else:
return 'b'
def bar(items):
results = []
for item in items:
results.append(foo(item))
return results
test_my_module_64443736.py
:
from unittest import TestCase, main
from unittest.mock import patch
from my_module_64443736 import bar
class TestCaseBar(TestCase):
@patch('my_module_64443736.foo')
def test_bar(self, mock_foo):
def dynamicMock(i):
if i == 'this':
return 'teresa teng'
else:
return 'best singer'
mock_foo.side_effect = dynamicMock
items = ['this', 'that']
result = bar(items)
self.assertEqual(result, ['teresa teng', 'best singer'])
self.assertTrue(mock_foo.call_count, 2)
if __name__ == '__main__':
main()
单元测试结果:
.
----------------------------------------------------------------------
Ran 1 test in 0.000s
OK
Name Stmts Miss Cover Missing
-------------------------------------------------------------------------------------
src/Whosebug/64443736/my_module_64443736.py 9 3 67% 2-5
src/Whosebug/64443736/test_my_module_64443736.py 16 0 100%
-------------------------------------------------------------------------------------
TOTAL 25 3 88%