如何在 python 中模拟依赖
how to mock dependency in python
我是 python 单元测试框架的新手,在模拟依赖方面有很多困惑。
我正在尝试为 class、(check_something()
):
的以下成员函数编写单元测试
class Validations:
def check_something(self):
abc = os.environ['PLATFORM']
xyz = Node()
no_of_nodes = len(xyz.some_type_var)
if abc != "X_PLATFORM" or no_of_nodes != 1:
raise someException()
我们如何消除依赖性?
- 需要模拟
Node()
?
- 我们如何确保
abc
分配给 X_PLATFORM
?
如何将值1
赋值给变量no_of_nodes
?这又是从 Node()
对象派生的。
class Node(object):
def __init__(self):
self.nodes = DEF()
self.some_type_var = someclass().getType()
self.localnode = os.environ['HOSTNAME']
self.peertype = self.get_peer_type()
def get_peer_type(self):
return node
我试着写下面的单元测试。我无法检查失败和通过条件。我不确定它是否正确。
class TestValidation(unittest.TestCase):
@mock.patch.object(Node, "get_peer_type")
@mock.patch('somefile.Node', spec=True)
def test_1(self, mock_object1, mock_object2):
os.environ['PLATFORM'] = 'X_PLATFORM'
obj = Validations()
self.assertRaises(someException, obj.check_something)
验证 class 使用 Node()
Class 对象,节点 class 使用其他一些 class.
- 如何根据条件确定是否引发异常?
是的,您可以模拟被测代码单元外部的任何内容。这里指的是 os.environ
字典和 Node()
class.
补丁需要应用到您的代码所在的模块;如果 somefile
与 Validations
是同一个模块,则 @mock.patch('somefile.Node', spec=True)
是正确的;看看 Where to patch section 为什么会这样。
我不确定使用 spec=True
在这里是否有用;您的 Node
属性是在 Node.__init__
中创建的所有实例属性,因此它们在 class 中不可用,这正是规范所告知的内容。如果您真的想设置规格,请参阅 autospeccing 部分了解如何克服这个问题。
abc
是从 os.environ
设置的,您可以使用 patch.dict()
object 来根据需要修补该词典。
xyz = len(xyz.some_type_var)
只需将 some_type_var
属性设置为具有正确长度的对象, 或 通过设置 xyz.some_type_var.__len__.return_value
,因为它是为 len()
函数调用的 xyz.some_type_var.__len__()
方法。
因此,要进行测试,您需要这样做:
class TestValidation(unittest.TestCase):
@mock.patch('somefile.Node')
def test_1(self, mock_node):
# set up the Node() instance, with the correct length
node_instance = mock_node.return_value
node_instance.some_type_var.__len__ = 2
# or, alternatively, node_instance.some_type_var = (1, 2)
# set up os.environ['PLATFORM']
with mock.patch.dict('os.environ', PLATFORM='X_PLATFORM'):
obj = Validations()
with self.assertRaises(someException):
obj.check_something()
我是 python 单元测试框架的新手,在模拟依赖方面有很多困惑。
我正在尝试为 class、(check_something()
):
class Validations:
def check_something(self):
abc = os.environ['PLATFORM']
xyz = Node()
no_of_nodes = len(xyz.some_type_var)
if abc != "X_PLATFORM" or no_of_nodes != 1:
raise someException()
我们如何消除依赖性?
- 需要模拟
Node()
? - 我们如何确保
abc
分配给X_PLATFORM
? 如何将值
1
赋值给变量no_of_nodes
?这又是从Node()
对象派生的。class Node(object): def __init__(self): self.nodes = DEF() self.some_type_var = someclass().getType() self.localnode = os.environ['HOSTNAME'] self.peertype = self.get_peer_type() def get_peer_type(self): return node
我试着写下面的单元测试。我无法检查失败和通过条件。我不确定它是否正确。
class TestValidation(unittest.TestCase):
@mock.patch.object(Node, "get_peer_type")
@mock.patch('somefile.Node', spec=True)
def test_1(self, mock_object1, mock_object2):
os.environ['PLATFORM'] = 'X_PLATFORM'
obj = Validations()
self.assertRaises(someException, obj.check_something)
验证 class 使用 Node()
Class 对象,节点 class 使用其他一些 class.
- 如何根据条件确定是否引发异常?
是的,您可以模拟被测代码单元外部的任何内容。这里指的是 os.environ
字典和 Node()
class.
补丁需要应用到您的代码所在的模块;如果 somefile
与 Validations
是同一个模块,则 @mock.patch('somefile.Node', spec=True)
是正确的;看看 Where to patch section 为什么会这样。
我不确定使用 spec=True
在这里是否有用;您的 Node
属性是在 Node.__init__
中创建的所有实例属性,因此它们在 class 中不可用,这正是规范所告知的内容。如果您真的想设置规格,请参阅 autospeccing 部分了解如何克服这个问题。
abc
是从 os.environ
设置的,您可以使用 patch.dict()
object 来根据需要修补该词典。
xyz = len(xyz.some_type_var)
只需将 some_type_var
属性设置为具有正确长度的对象, 或 通过设置 xyz.some_type_var.__len__.return_value
,因为它是为 len()
函数调用的 xyz.some_type_var.__len__()
方法。
因此,要进行测试,您需要这样做:
class TestValidation(unittest.TestCase):
@mock.patch('somefile.Node')
def test_1(self, mock_node):
# set up the Node() instance, with the correct length
node_instance = mock_node.return_value
node_instance.some_type_var.__len__ = 2
# or, alternatively, node_instance.some_type_var = (1, 2)
# set up os.environ['PLATFORM']
with mock.patch.dict('os.environ', PLATFORM='X_PLATFORM'):
obj = Validations()
with self.assertRaises(someException):
obj.check_something()