Add a new mockpatch fixture

This fixture provides an easy usage for mock (unittest.mock in
Python 3).
This commit is contained in:
Julien Danjou
2015-02-09 15:21:11 +01:00
committed by Robert Collins
parent 8baf138829
commit 08be09df43
6 changed files with 161 additions and 0 deletions

View File

@@ -54,6 +54,9 @@ __all__ = [
'LogHandler',
'LoggerFixture',
'MethodFixture',
'MockPatch',
'MockPatchMultiple',
'MockPatchObject',
'MonkeyPatch',
'NestedTempfile',
'PackagePathEntry',
@@ -86,6 +89,9 @@ from fixtures._fixtures import (
FakePopen,
LoggerFixture,
LogHandler,
MockPatch,
MockPatchMultiple,
MockPatchObject,
MonkeyPatch,
NestedTempfile,
PackagePathEntry,

View File

@@ -25,6 +25,9 @@ __all__ = [
'FakePopen',
'LoggerFixture',
'LogHandler',
'MockPatch',
'MockPatchMultiple',
'MockPatchObject',
'MonkeyPatch',
'NestedTempfile',
'PackagePathEntry',
@@ -49,6 +52,11 @@ from fixtures._fixtures.logger import (
LoggerFixture,
LogHandler,
)
from fixtures._fixtures.mockpatch import (
MockPatch,
MockPatchMultiple,
MockPatchObject,
)
from fixtures._fixtures.monkeypatch import MonkeyPatch
from fixtures._fixtures.popen import (
FakePopen,

View File

@@ -0,0 +1,71 @@
# Copyright 2010 United States Government as represented by the
# Administrator of the National Aeronautics and Space Administration.
# Copyright 2013 Hewlett-Packard Development Company, L.P.
# All Rights Reserved.
#
# Licensed under the Apache License, Version 2.0 (the "License"); you may
# not use this file except in compliance with the License. You may obtain
# a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
# License for the specific language governing permissions and limitations
# under the License.
import fixtures
try:
from unittest import mock
except ImportError:
import mock
class _Base(fixtures.Fixture):
def setUp(self):
super(_Base, self).setUp()
_p = self._get_p()
self.addCleanup(_p.stop)
self.mock = _p.start()
class MockPatchObject(_Base):
"""Deal with code around mock."""
def __init__(self, obj, attr, new=mock.DEFAULT, **kwargs):
super(MockPatchObject, self).__init__()
self._get_p = lambda: mock.patch.object(obj, attr, new, **kwargs)
class MockPatch(_Base):
"""Deal with code around mock.patch."""
def __init__(self, obj, new=mock.DEFAULT, **kwargs):
super(MockPatch, self).__init__()
self._get_p = lambda: mock.patch(obj, new, **kwargs)
class MockPatchMultiple(_Base):
"""Deal with code around mock.patch.multiple."""
# Default value to trigger a MagicMock to be created for a named
# attribute.
DEFAULT = mock.DEFAULT
def __init__(self, obj, **kwargs):
"""Initialize the mocks
Pass name=value to replace obj.name with value.
Pass name=Multiple.DEFAULT to replace obj.name with a
MagicMock instance.
:param obj: Object or name containing values being mocked.
:type obj: str or object
:param kwargs: names and values of attributes of obj to be mocked.
"""
super(MockPatchMultiple, self).__init__()
self._get_p = lambda: mock.patch.multiple(obj, **kwargs)

View File

@@ -17,6 +17,7 @@ def load_tests(loader, standard_tests, pattern):
test_modules = [
'environ',
'logger',
'mockpatch',
'monkeypatch',
'packagepath',
'popen',

View File

@@ -0,0 +1,74 @@
# Copyright 2014 IBM Corp.
#
# Licensed under the Apache License, Version 2.0 (the "License"); you may
# not use this file except in compliance with the License. You may obtain
# a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
# License for the specific language governing permissions and limitations
# under the License.
try:
from unittest import mock
except ImportError:
import mock
import testtools
from fixtures import (
MockPatch,
MockPatchMultiple,
MockPatchObject,
)
class Foo(object):
def bar(self):
return self
def mocking_bar(self):
return 'mocked!'
class TestMockPatch(testtools.TestCase):
def test_mock_patch_with_replacement(self):
self.useFixture(MockPatch('%s.Foo.bar' % (__name__), mocking_bar))
instance = Foo()
self.assertEqual(instance.bar(), 'mocked!')
def test_mock_patch_without_replacement(self):
self.useFixture(MockPatch('%s.Foo.bar' % (__name__)))
instance = Foo()
self.assertIsInstance(instance.bar(), mock.MagicMock)
class TestMockMultiple(testtools.TestCase):
def test_mock_multiple_with_replacement(self):
self.useFixture(MockPatchMultiple('%s.Foo' % (__name__),
bar=mocking_bar))
instance = Foo()
self.assertEqual(instance.bar(), 'mocked!')
def test_mock_patch_without_replacement(self):
self.useFixture(MockPatchMultiple(
'%s.Foo' % (__name__),
bar=MockPatchMultiple.DEFAULT))
instance = Foo()
self.assertIsInstance(instance.bar(), mock.MagicMock)
class TestMockPatchObject(testtools.TestCase):
def test_mock_patch_object_with_replacement(self):
self.useFixture(MockPatchObject(Foo, 'bar', mocking_bar))
instance = Foo()
self.assertEqual(instance.bar(), 'mocked!')
def test_mock_patch_object_without_replacement(self):
self.useFixture(MockPatchObject(Foo, 'bar'))
instance = Foo()
self.assertIsInstance(instance.bar(), mock.MagicMock)

View File

@@ -1,2 +1,3 @@
pbr>=0.11
testtools>=0.9.22
mock