mirror of
https://github.com/python/cpython.git
synced 2025-10-03 21:55:41 +00:00
Make unittest.mock.create_autospec resilient against AttributeError on original object
This commit is contained in:
parent
899ee613f7
commit
656319e58d
2 changed files with 29 additions and 2 deletions
|
@ -2044,10 +2044,14 @@ def create_autospec(spec, spec_set=False, instance=False, _parent=None,
|
||||||
# object to mock it so we would rather trigger a property than mock
|
# object to mock it so we would rather trigger a property than mock
|
||||||
# the property descriptor. Likewise we want to mock out dynamically
|
# the property descriptor. Likewise we want to mock out dynamically
|
||||||
# provided attributes.
|
# provided attributes.
|
||||||
# XXXX what about attributes that raise exceptions on being fetched
|
# XXXX what about attributes that raise exceptions other than
|
||||||
|
# AttributeError on being fetched?
|
||||||
# we could be resilient against it, or catch and propagate the
|
# we could be resilient against it, or catch and propagate the
|
||||||
# exception when the attribute is fetched from the mock
|
# exception when the attribute is fetched from the mock
|
||||||
|
try:
|
||||||
original = getattr(spec, entry)
|
original = getattr(spec, entry)
|
||||||
|
except AttributeError:
|
||||||
|
continue
|
||||||
|
|
||||||
kwargs = {'spec': original}
|
kwargs = {'spec': original}
|
||||||
if spec_set:
|
if spec_set:
|
||||||
|
|
|
@ -651,6 +651,29 @@ class SpecSignatureTest(unittest.TestCase):
|
||||||
mock.f.assert_called_with(3, 4)
|
mock.f.assert_called_with(3, 4)
|
||||||
|
|
||||||
|
|
||||||
|
def test_skip_attributeerrors(self):
|
||||||
|
class Raiser(object):
|
||||||
|
def __get__(self, obj, type=None):
|
||||||
|
if obj is None:
|
||||||
|
raise AttributeError('Can only be accessed via an instance')
|
||||||
|
|
||||||
|
class RaiserClass(object):
|
||||||
|
raiser = Raiser()
|
||||||
|
|
||||||
|
@staticmethod
|
||||||
|
def existing(a, b):
|
||||||
|
return a + b
|
||||||
|
|
||||||
|
s = create_autospec(RaiserClass)
|
||||||
|
self.assertRaises(TypeError, lambda x: s.existing(1, 2, 3))
|
||||||
|
s.existing(1, 2)
|
||||||
|
self.assertRaises(AttributeError, lambda: s.nonexisting)
|
||||||
|
|
||||||
|
# check we can fetch the raiser attribute and it has no spec
|
||||||
|
obj = s.raiser
|
||||||
|
obj.foo, obj.bar
|
||||||
|
|
||||||
|
|
||||||
def test_signature_class(self):
|
def test_signature_class(self):
|
||||||
class Foo(object):
|
class Foo(object):
|
||||||
def __init__(self, a, b=3):
|
def __init__(self, a, b=3):
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue