一种简单的方法来模拟松散定义的Python dict对象

Mar*_*ang 6 python unit-testing python-mock python-unittest

有没有一种简单的方法来在Python中模拟松散定义的dict对象?例如,如何在给定dict的情况下轻松表达input,我想检查其中的每个值是否符合特定的元定义,如最小值和最大值,长度和类型?

能够这样做可能很方便,例如,在编写测试时.

mock(Python版本3.3+中的unittest.mock)中,可以指定值可以是ANY值,例如

>>> mock = Mock(return_value=None)
>>> mock('foo', bar=object())
>>> mock.assert_called_once_with('foo', bar=ANY)
Run Code Online (Sandbox Code Playgroud)

但是,如果bar上面应该是类似dict的对象,就像

>>> {'baz': <an integer between -3 and 14>, 'qux': <'yes' or 'no'>}
Run Code Online (Sandbox Code Playgroud)

Mar*_*ang 5

我实际上编写了AnyValid,一个利用formencodeunittest.mock中实现的伟大工作的最小库来处理这种情况.

例如,测试如上所述的dict对象可以表示为

>>> from mock import Mock
>>> from any_valid import AnyValid, Int, OneOf
>>> valid_bar = {
...     'baz': AnyValid(Int(min=-3, max=14)),
...     'qux': AnyValid(OneOf(['yes', 'no'])),
...     }
>>> mock = Mock(return_value=None)
>>> mock('foo', bar={'baz': 4, 'qux': 'yes'})
>>> mock.assert_called_once_with('foo', bar=valid_bar)
>>>
Run Code Online (Sandbox Code Playgroud)

因为AnyValid可以从formencode中的大量验证器中获取任何验证器,所以可以以类似表达的方式指定许多其他条件.