Add a test utility for checking mock calls with objects

This adds a test utility that mirrors the mock.called_with() and
mock.called_once_with() utilities, but which uses naive object
comparisons to simplify things.

Change-Id: I83811b302b8579f8f8539d974aca657a3211d2c7
This commit is contained in:
Dan Smith 2016-06-24 07:54:47 -07:00 committed by paul-carlton2
parent 1cb9195aa8
commit ba7077b829
2 changed files with 106 additions and 0 deletions

View File

@ -37,7 +37,10 @@ import six
import nova import nova
from nova import context from nova import context
from nova import exception from nova import exception
from nova.objects import base as obj_base
from nova import test from nova import test
from nova.tests.unit.objects import test_objects
from nova.tests.unit import utils as test_utils
from nova import utils from nova import utils
CONF = cfg.CONF CONF = cfg.CONF
@ -1348,3 +1351,66 @@ class UT8TestCase(test.NoDBTestCase):
def test_text_type_with_encoding(self): def test_text_type_with_encoding(self):
some_value = 'test\u2026config' some_value = 'test\u2026config'
self.assertEqual(some_value, utils.utf8(some_value).decode("utf-8")) self.assertEqual(some_value, utils.utf8(some_value).decode("utf-8"))
class TestObjectCallHelpers(test.NoDBTestCase):
def test_with_primitives(self):
tester = mock.Mock()
tester.foo(1, 'two', three='four')
self.assertTrue(
test_utils.obj_called_with(tester.foo, 1, 'two', three='four'))
self.assertFalse(
test_utils.obj_called_with(tester.foo, 42, 'two', three='four'))
def test_with_object(self):
obj_base.NovaObjectRegistry.register(test_objects.MyObj)
obj = test_objects.MyObj(foo=1, bar='baz')
tester = mock.Mock()
tester.foo(1, obj)
self.assertTrue(
test_utils.obj_called_with(
tester.foo, 1,
test_objects.MyObj(foo=1, bar='baz')))
self.assertFalse(
test_utils.obj_called_with(
tester.foo, 1,
test_objects.MyObj(foo=2, bar='baz')))
def test_with_object_multiple(self):
obj_base.NovaObjectRegistry.register(test_objects.MyObj)
obj1 = test_objects.MyObj(foo=1, bar='baz')
obj2 = test_objects.MyObj(foo=3, bar='baz')
tester = mock.Mock()
tester.foo(1, obj1)
tester.foo(1, obj1)
tester.foo(3, obj2)
# Called at all
self.assertTrue(
test_utils.obj_called_with(
tester.foo, 1,
test_objects.MyObj(foo=1, bar='baz')))
# Called once (not true)
self.assertFalse(
test_utils.obj_called_once_with(
tester.foo, 1,
test_objects.MyObj(foo=1, bar='baz')))
# Not called with obj.foo=2
self.assertFalse(
test_utils.obj_called_with(
tester.foo, 1,
test_objects.MyObj(foo=2, bar='baz')))
# Called with obj.foo.3
self.assertTrue(
test_utils.obj_called_with(
tester.foo, 3,
test_objects.MyObj(foo=3, bar='baz')))
# Called once with obj.foo.3
self.assertTrue(
test_utils.obj_called_once_with(
tester.foo, 3,
test_objects.MyObj(foo=3, bar='baz')))

View File

@ -28,6 +28,7 @@ from nova.image import glance
from nova.network import minidns from nova.network import minidns
from nova.network import model as network_model from nova.network import model as network_model
from nova import objects from nova import objects
from nova.objects import base as obj_base
import nova.utils import nova.utils
CONF = nova.conf.CONF CONF = nova.conf.CONF
@ -247,3 +248,42 @@ def is_ipv6_supported():
def get_api_version(request): def get_api_version(request):
if request.path[2:3].isdigit(): if request.path[2:3].isdigit():
return int(request.path[2:3]) return int(request.path[2:3])
def compare_obj_primitive(thing1, thing2):
if isinstance(thing1, obj_base.NovaObject):
return thing1.obj_to_primitive() == thing2.obj_to_primitive()
else:
return thing1 == thing2
def _compare_args(args1, args2, cmp):
return all(cmp(*pair) for pair in zip(args1, args2))
def _compare_kwargs(kwargs1, kwargs2, cmp):
return all(cmp(kwargs1[k], kwargs2[k])
for k in set(list(kwargs1.keys()) + list(kwargs2.keys())))
def _obj_called_with(the_mock, *args, **kwargs):
if 'obj_cmp' in kwargs:
cmp = kwargs.pop('obj_cmp')
else:
cmp = compare_obj_primitive
count = 0
for call in the_mock.call_args_list:
if (_compare_args(call[0], args, cmp) and
_compare_kwargs(call[1], kwargs, cmp)):
count += 1
return count
def obj_called_with(the_mock, *args, **kwargs):
return _obj_called_with(the_mock, *args, **kwargs) != 0
def obj_called_once_with(the_mock, *args, **kwargs):
return _obj_called_with(the_mock, *args, **kwargs) == 1