cpython: adc1fc2dc872 (original) (raw)

--- a/Doc/library/development.rst +++ b/Doc/library/development.rst @@ -19,5 +19,11 @@ The list of modules described in this ch pydoc.rst doctest.rst unittest.rst

new file mode 100644 --- /dev/null +++ b/Doc/library/unittest.mock-examples.rst @@ -0,0 +1,887 @@ +.. _further-examples: + +:mod:unittest.mock --- further examples +========================================= + +.. module:: unittest.mock

+.. versionadded:: 3.3 + + +Here are some more examples for some slightly more advanced scenarios than in +the :ref:getting started <getting-started> guide. + + +Mocking chained calls +--------------------- + +Mocking chained calls is actually straightforward with mock once you +understand the :attr:~Mock.return_value attribute. When a mock is called for +the first time, or you fetch its return_value before it has been called, a +new Mock is created. + +This means that you can see how the object returned from a call to a mocked +object has been used by interrogating the return_value mock: +

+ +From here it is a simple step to configure and then make assertions about +chained calls. Of course another alternative is writing your code in a more +testable way in the first place... + +So, suppose we have some code that looks a little bit like this: +

+ +Assuming that BackendProvider is already well tested, how do we test +method()? Specifically, we want to test that the code section # more[](#l2.52) +code uses the response object in the correct way. + +As this chain of calls is made from an instance attribute we can monkey patch +the backend attribute on a Something instance. In this particular case +we are only interested in the return value from the final call to +start_call so we don't have much configuration to do. Let's assume the +object it returns is 'file-like', so we'll ensure that our response object +uses the builtin file as its spec. + +To do this we create a mock instance as our mock backend and create a mock +response object for it. To set the response as the return value for that final +start_call we could do this: +

+ +We can do that in a slightly nicer way using the :meth:~Mock.configure_mock +method to directly set the return value for us: +

+ +With these we monkey patch the "mock backend" in place and can make the real +call: +

+ +Using :attr:~Mock.mock_calls we can check the chained call with a single +assert. A chained call is several calls in one line of code, so there will be +several entries in mock_calls. We can use :meth:call.call_list to create +this list of calls for us: +

+ + +Partial mocking +--------------- + +In some tests I wanted to mock out a call to datetime.date.today()[](#l2.96) +<http://docs.python.org/library/datetime.html#datetime.date.today>_ to return +a known date, but I didn't want to prevent the code under test from +creating new date objects. Unfortunately datetime.date is written in C, and +so I couldn't just monkey-patch out the static date.today method. + +I found a simple way of doing this that involved effectively wrapping the date +class with a mock, but passing through calls to the constructor to the real +class (and returning real instances). + +The :func:patch decorator <patch> is used here to +mock out the date class in the module under test. The :attr:side_effect +attribute on the mock date class is then set to a lambda function that returns +a real date. When the mock date class is called a real date will be +constructed and returned by side_effect. +

+ +Note that we don't patch datetime.date globally, we patch date in the +module that uses it. See :ref:where to patch <where-to-patch>. + +When date.today() is called a known date is returned, but calls to the +date(...) constructor still return normal dates. Without this you can find +yourself having to calculate an expected result using exactly the same +algorithm as the code under test, which is a classic testing anti-pattern. + +Calls to the date constructor are recorded in the mock_date attributes +(call_count and friends) which may also be useful for your tests. + +An alternative way of dealing with mocking dates, or other builtin classes, +is discussed in this blog entry[](#l2.133) +<http://williamjohnbert.com/2011/07/how-to-unit-testing-in-django-with-mocking-and-patching/>. + + +Mocking a Generator Method +-------------------------- + +A Python generator is a function or method that uses the yield statement[](#l2.140) +<http://docs.python.org/reference/simple_stmts.html#the-yield-statement> to +return a series of values when iterated over [#]. + +A generator method / function is called to return the generator object. It is +the generator object that is then iterated over. The protocol method for +iteration is __iter__[](#l2.146) +<http://docs.python.org/library/stdtypes.html#container.__iter__>, so we can +mock this using a MagicMock. + +Here's an example class with an "iter" method implemented as a generator: +

+ + +How would we mock this class, and in particular its "iter" method? + +To configure the values returned from the iteration (implicit in the call to +list), we need to configure the object returned by the call to foo.iter(). +

+ +.. [#] There are also generator expressions and more `advanced uses

+ + +Applying the same patch to every test method +-------------------------------------------- + +If you want several patches in place for multiple test methods the obvious way +is to apply the patch decorators to every method. This can feel like unnecessary +repetition. For Python 2.6 or more recent you can use patch (in all its +various forms) as a class decorator. This applies the patches to all test +methods on the class. A test method is identified by methods whose names start +with test: +

+ +An alternative way of managing patches is to use the :ref:start-and-stop. +These allow you to move the patching into your setUp and tearDown methods. +

+ +If you use this technique you must ensure that the patching is "undone" by +calling stop. This can be fiddlier than you might think, because if an +exception is raised in the setUp then tearDown is not called. +:meth:unittest.TestCase.addCleanup makes this easier: +

+ + +Mocking Unbound Methods +----------------------- + +Whilst writing tests today I needed to patch an unbound method (patching the +method on the class rather than on the instance). I needed self to be passed +in as the first argument because I want to make asserts about which objects +were calling this particular method. The issue is that you can't patch with a +mock for this, because if you replace an unbound method with a mock it doesn't +become a bound method when fetched from the instance, and so it doesn't get +self passed in. The workaround is to patch the unbound method with a real +function instead. The :func:patch decorator makes it so simple to +patch out methods with a mock that having to create a real function becomes a +nuisance. + +If you pass autospec=True to patch then it does the patching with a +real function object. This function object has the same signature as the one +it is replacing, but delegates to a mock under the hood. You still get your +mock auto-created in exactly the same way as before. What it means though, is +that if you use it to patch out an unbound method on a class the mocked +function will be turned into a bound method if it is fetched from an instance. +It will have self passed in as the first argument, which is exactly what I +wanted: +

+ +If we don't use autospec=True then the unbound method is patched out +with a Mock instance instead, and isn't called with self. + + +Checking multiple calls with mock +--------------------------------- + +mock has a nice API for making assertions about how your mock objects are used. +

+ +If your mock is only being called once you can use the +:meth:assert_called_once_with method that also asserts that the +:attr:call_count is one. +

+ +Both assert_called_with and assert_called_once_with make assertions about +the most recent call. If your mock is going to be called several times, and +you want to make assertions about all those calls you can use +:attr:~Mock.call_args_list: +

+ +The :data:call helper makes it easy to make assertions about these calls. You +can build up a list of expected calls and compare it to call_args_list. This +looks remarkably similar to the repr of the call_args_list: +

+ + +Coping with mutable arguments +----------------------------- + +Another situation is rare, but can bite you, is when your mock is called with +mutable arguments. call_args and call_args_list store references to the +arguments. If the arguments are mutated by the code under test then you can no +longer make assertions about what the values were when the mock was called. + +Here's some example code that shows the problem. Imagine the following functions +defined in 'mymodule':: +

+

+ +When we try to test that grob calls frob with the correct argument look +what happens: +

+ +One possibility would be for mock to copy the arguments you pass in. This +could then cause problems if you do assertions that rely on object identity +for equality. + +Here's one solution that uses the :attr:side_effect +functionality. If you provide a side_effect function for a mock then +side_effect will be called with the same args as the mock. This gives us an +opportunity to copy the arguments and store them for later assertions. In this +example I'm using another mock to store the arguments so that I can use the +mock methods for doing the assertion. Again a helper function sets this up for +me. +

+ +copy_call_args is called with the mock that will be called. It returns a new +mock that we do the assertion on. The side_effect function makes a copy of +the args and calls our new_mock with the copy. + +.. note:: +

+

+ +An alternative approach is to create a subclass of Mock or MagicMock that +copies (using :func:copy.deepcopy) the arguments. +Here's an example implementation: +

+ +When you subclass Mock or MagicMock all dynamically created attributes, +and the return_value will use your subclass automatically. That means all +children of a CopyingMock will also have the type CopyingMock. + + +Multiple calls with different effects +------------------------------------- + +Handling code that needs to behave differently on subsequent calls during the +test can be tricky. For example you may have a function that needs to raise +an exception the first time it is called but returns a response on the second +call (testing retry behaviour). + +One approach is to use a :attr:side_effect function that replaces itself. The +first time it is called the side_effect sets a new side_effect that will +be used for the second call. It then raises an exception: +

+ +Another perfectly valid way would be to pop return values from a list. If the +return value is an exception, raise it instead of returning it: +

+ +Which approach you prefer is a matter of taste. The first approach is actually +a line shorter but maybe the second approach is more readable. + + +Nesting Patches +--------------- + +Using patch as a context manager is nice, but if you do multiple patches you +can end up with nested with statements indenting further and further to the +right: +

+ +With unittest cleanup functions and the :ref:start-and-stop we can +achieve the same effect without the nested indentation. A simple helper +method, create_patch, puts the patch in place and returns the created mock +for us: +

+ + +Mocking a dictionary with MagicMock +----------------------------------- + +You may want to mock a dictionary, or other container object, recording all +access to it whilst having it still behave like a dictionary. + +We can do this with :class:MagicMock, which will behave like a dictionary, +and using :data:~Mock.side_effect to delegate dictionary access to a real +underlying dictionary that is under our control. + +When the __getitem__ and __setitem__ methods of our MagicMock are called +(normal dictionary access) then side_effect is called with the key (and in +the case of __setitem__ the value too). We can also control what is returned. + +After the MagicMock has been used we can use attributes like +:data:~Mock.call_args_list to assert about how the dictionary was used: +

+ +.. note:: +

+

+

+

+ +With these side effect functions in place, the mock will behave like a normal +dictionary but recording the access. It even raises a KeyError if you try +to access a key that doesn't exist. +

+ +After it has been used you can make assertions about the access using the normal +mock methods and attributes: +

+ + +Mock subclasses and their attributes +------------------------------------ + +There are various reasons why you might want to subclass Mock. One reason +might be to add helper methods. Here's a silly example: +

+ +The standard behaviour for Mock instances is that attributes and the return +value mocks are of the same type as the mock they are accessed on. This ensures +that Mock attributes are Mocks and MagicMock attributes are MagicMocks +[#]_. So if you're subclassing to add helper methods then they'll also be +available on the attributes and return value mock of instances of your +subclass. +

+ +Sometimes this is inconvenient. For example, one user[](#l2.644) +<https://code.google.com/p/mock/issues/detail?id=105>_ is subclassing mock to +created a Twisted adaptor[](#l2.646) +<http://twistedmatrix.com/documents/11.0.0/api/twisted.python.components.html>_. +Having this applied to attributes too actually causes errors. + +Mock (in all its flavours) uses a method called _get_child_mock to create +these "sub-mocks" for attributes and return values. You can prevent your +subclass being used for attributes by overriding this method. The signature is +that it takes arbitrary keyword arguments (**kwargs) which are then passed +onto the mock constructor: +

+ +.. [#] An exception to this rule are the non-callable mocks. Attributes use the

+ + +Mocking imports with patch.dict +------------------------------- + +One situation where mocking can be hard is where you have a local import inside +a function. These are harder to mock because they aren't using an object from +the module namespace that we can patch out. + +Generally local imports are to be avoided. They are sometimes done to prevent +circular dependencies, for which there is usually a much better way to solve +the problem (refactor the code) or to prevent "up front costs" by delaying the +import. This can also be solved in better ways than an unconditional local +import (store the module as a class or module attribute and only do the import +on first use). + +That aside there is a way to use mock to affect the results of an import. +Importing fetches an object from the sys.modules dictionary. Note that it +fetches an object, which need not be a module. Importing a module for the +first time results in a module object being put in sys.modules, so usually +when you import something you get a module back. This need not be the case +however. + +This means you can use :func:patch.dict to temporarily put a mock in place +in sys.modules. Any imports whilst this patch is active will fetch the mock. +When the patch is complete (the decorated function exits, the with statement +body is complete or patcher.stop() is called) then whatever was there +previously will be restored safely. + +Here's an example that mocks out the 'fooble' module. +

+ +As you can see the import fooble succeeds, but on exit there is no 'fooble' +left in sys.modules. + +This also works for the from module import name form: +

+ +With slightly more work you can also mock package imports: +

+ + +Tracking order of calls and less verbose call assertions +-------------------------------------------------------- + +The :class:Mock class allows you to track the order of method calls on +your mock objects through the :attr:~Mock.method_calls attribute. This +doesn't allow you to track the order of calls between separate mock objects, +however we can use :attr:~Mock.mock_calls to achieve the same effect. + +Because mocks track calls to child mocks in mock_calls, and accessing an +arbitrary attribute of a mock creates a child mock, we can create our separate +mocks from a parent one. Calls to those child mock will then all be recorded, +in order, in the mock_calls of the parent: +

+

+

+ +We can then assert about the calls, including the order, by comparing with +the mock_calls attribute on the manager mock: +

+ +If patch is creating, and putting in place, your mocks then you can attach +them to a manager mock using the :meth:~Mock.attach_mock method. After +attaching calls will be recorded in mock_calls of the manager. +

+ +If many calls have been made, but you're only interested in a particular +sequence of them then an alternative is to use the +:meth:~Mock.assert_has_calls method. This takes a list of calls (constructed +with the :data:call object). If that sequence of calls are in +:attr:~Mock.mock_calls then the assert succeeds. +

+ +Even though the chained call m.one().two().three() aren't the only calls that +have been made to the mock, the assert still succeeds. + +Sometimes a mock may have several calls made to it, and you are only interested +in asserting about some of those calls. You may not even care about the +order. In this case you can pass any_order=True to assert_has_calls: +

+ + +More complex argument matching +------------------------------ + +Using the same basic concept as :data:ANY we can implement matchers to do more +complex assertions on objects used as arguments to mocks. + +Suppose we expect some object to be passed to a mock that by default +compares equal based on object identity (which is the Python default for user +defined classes). To use :meth:~Mock.assert_called_with we would need to pass +in the exact same object. If we are only interested in some of the attributes +of this object then we can create a matcher that will check these attributes +for us. + +You can see in this example how a 'standard' call to assert_called_with isn't +sufficient: +

+ +A comparison function for our Foo class might look something like this: +

+ +And a matcher object that can use comparison functions like this for its +equality operation would look something like this: +

+ +Putting all this together: +

+ +The Matcher is instantiated with our compare function and the Foo object +we want to compare against. In assert_called_with the Matcher equality +method will be called, which compares the object the mock was called with +against the one we created our matcher with. If they match then +assert_called_with passes, and if they don't an AssertionError is raised: +

+ +With a bit of tweaking you could have the comparison function raise the +AssertionError directly and provide a more useful failure message. + +As of version 1.5, the Python testing library PyHamcrest[](#l2.887) +<http://pypi.python.org/pypi/PyHamcrest>_ provides similar functionality, +that may be useful here, in the form of its equality matcher +(hamcrest.library.integration.match_equality[](#l2.890) +<http://packages.python.org/PyHamcrest/integration.html#hamcrest.library.integration.match_equality>_).

new file mode 100644 --- /dev/null +++ b/Doc/library/unittest.mock-getting-started.rst @@ -0,0 +1,419 @@ +:mod:unittest.mock --- getting started +======================================== + +.. module:: unittest.mock

+.. versionadded:: 3.3 + + +.. _getting-started: + +Using Mock +---------- + +Mock Patching Methods +~~~~~~~~~~~~~~~~~~~~~ + +Common uses for :class:Mock objects include: + +* Patching methods +* Recording method calls on objects + +You might want to replace a method on an object to check that +it is called with the correct arguments by another part of the system: +

+ +Once our mock has been used (real.method in this example) it has methods +and attributes that allow you to make assertions about how it has been used. + +.. note:: +

+ +Once the mock has been called its :attr:~Mock.called attribute is set to +True. More importantly we can use the :meth:~Mock.assert_called_with or +:meth~Mock.assert_called_once_with method to check that it was called with +the correct arguments. + +This example tests that calling ProductionClass().method results in a call to +the something method: +

+ + + +Mock for Method Calls on an Object +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +In the last example we patched a method directly on an object to check that it +was called correctly. Another common use case is to pass an object into a +method (or some part of the system under test) and then check that it is used +in the correct way. + +The simple ProductionClass below has a closer method. If it is called with +an object then it calls close on it. +

+ +So to test it we need to pass in an object with a close method and check +that it was called correctly. +

+ +We don't have to do any work to provide the 'close' method on our mock. +Accessing close creates it. So, if 'close' hasn't already been called then +accessing it in the test will create it, but :meth:~Mock.assert_called_with +will raise a failure exception. + + +Mocking Classes +~~~~~~~~~~~~~~~ + +A common use case is to mock out classes instantiated by your code under test. +When you patch a class, then that class is replaced with a mock. Instances +are created by calling the class. This means you access the "mock instance" +by looking at the return value of the mocked class. + +In the example below we have a function some_function that instantiates Foo +and calls a method on it. The call to patch replaces the class Foo with a +mock. The Foo instance is the result of calling the mock, so it is configured +by modify the mock :attr:~Mock.return_value. +

+ + +Naming your mocks +~~~~~~~~~~~~~~~~~ + +It can be useful to give your mocks a name. The name is shown in the repr of +the mock and can be helpful when the mock appears in test failure messages. The +name is also propagated to attributes or methods of the mock: +

+ + +Tracking all Calls +~~~~~~~~~~~~~~~~~~ + +Often you want to track more than a single call to a method. The +:attr:~Mock.mock_calls attribute records all calls +to child attributes of the mock - and also to their children. +

+ +If you make an assertion about mock_calls and any unexpected methods +have been called, then the assertion will fail. This is useful because as well +as asserting that the calls you expected have been made, you are also checking +that they were made in the right order and with no additional calls: + +You use the :data:call object to construct lists for comparing with +mock_calls: +

+ + +Setting Return Values and Attributes +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +Setting the return values on a mock object is trivially easy: +

+ +Of course you can do the same for methods on the mock: +

+ +The return value can also be set in the constructor: +

+ +If you need an attribute setting on your mock, just do it: +

+ +Sometimes you want to mock up a more complex situation, like for example +mock.connection.cursor().execute("SELECT 1"). If we wanted this call to +return a list, then we have to configure the result of the nested call. + +We can use :data:call to construct the set of calls in a "chained call" like +this for easy assertion afterwards: +

+ +It is the call to .call_list() that turns our call object into a list of +calls representing the chained calls. + + +Raising exceptions with mocks +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +A useful attribute is :attr:~Mock.side_effect. If you set this to an +exception class or instance then the exception will be raised when the mock +is called. +

+ + +Side effect functions and iterables +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +side_effect can also be set to a function or an iterable. The use case for +side_effect as an iterable is where your mock is going to be called several +times, and you want each call to return a different value. When you set +side_effect to an iterable every call to the mock returns the next value +from the iterable: +

+ + +For more advanced use cases, like dynamically varying the return values +depending on what the mock is called with, side_effect can be a function. +The function will be called with the same arguments as the mock. Whatever the +function returns is what the call returns: +

+ + +Creating a Mock from an Existing Object +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +One problem with over use of mocking is that it couples your tests to the +implementation of your mocks rather than your real code. Suppose you have a +class that implements some_method. In a test for another class, you +provide a mock of this object that also provides some_method. If later +you refactor the first class, so that it no longer has some_method - then +your tests will continue to pass even though your code is now broken + +Mock allows you to provide an object as a specification for the mock, +using the spec keyword argument. Accessing methods / attributes on the +mock that don't exist on your specification object will immediately raise an +attribute error. If you change the implementation of your specification, then +tests that use that class will start failing immediately without you having to +instantiate the class in those tests. +

+ +If you want a stronger form of specification that prevents the setting +of arbitrary attributes as well as the getting of them then you can use +spec_set instead of spec. + + + +Patch Decorators +---------------- + +.. note:: +

+ +A common need in tests is to patch a class attribute or a module attribute, +for example patching a builtin or patching a class in a module to test that it +is instantiated. Modules and classes are effectively global, so patching on +them has to be undone after the test or the patch will persist into other +tests and cause hard to diagnose problems. + +mock provides three convenient decorators for this: patch, patch.object and +patch.dict. patch takes a single string, of the form +package.module.Class.attribute to specify the attribute you are patching. It +also optionally takes a value that you want the attribute (or class or +whatever) to be replaced with. 'patch.object' takes an object and the name of +the attribute you would like patched, plus optionally the value to patch it +with. + +patch.object: +

+

+ +If you are patching a module (including __builtin__) then use patch +instead of patch.object: +

+ +The module name can be 'dotted', in the form package.module if needed: +

+ +A nice pattern is to actually decorate test methods themselves: +

+ +If you want to patch with a Mock, you can use patch with only one argument +(or patch.object with two arguments). The mock will be created for you and +passed into the test function / method: +

+ +You can stack up multiple patch decorators using this pattern: +

+ +When you nest patch decorators the mocks are passed in to the decorated +function in the same order they applied (the normal python order that +decorators are applied). This means from the bottom up, so in the example +above the mock for test_module.ClassName2 is passed in first. + +There is also :func:patch.dict for setting values in a dictionary just +during a scope and restoring the dictionary to its original state when the test +ends: +

+patch, patch.object and patch.dict can all be used as context managers. + +Where you use patch to create a mock for you, you can get a reference to the +mock using the "as" form of the with statement: +

+ + +As an alternative patch, patch.object and patch.dict can be used as +class decorators. When used in this way it is the same as applying the +decorator indvidually to every method whose name starts with "test". + +For some more advanced examples, see the :ref:further-examples page.

new file mode 100644 --- /dev/null +++ b/Doc/library/unittest.mock-helpers.rst @@ -0,0 +1,537 @@ +:mod:unittest.mock --- helpers +================================ + +.. module:: unittest.mock

+.. versionadded:: 3.3 + + +sentinel +-------- + +.. data:: sentinel +

+

+ +Sometimes when testing you need to test that a specific object is passed as an +argument to another method, or returned. It can be common to create named +sentinel objects to test this. sentinel provides a convenient way of +creating and testing the identity of objects like this. + +In this example we monkey patch method to return sentinel.some_object: +

+ + +DEFAULT +------- + + +.. data:: DEFAULT +

+ + + +call +---- + +.. function:: call(*args, **kwargs) +

+

+ +.. method:: call.call_list() +

+ +call_list is particularly useful for making assertions on "chained calls". A +chained call is multiple calls on a single line of code. This results in +multiple entries in :attr:~Mock.mock_calls on a mock. Manually constructing +the sequence of calls can be tedious. + +:meth:~call.call_list can construct the sequence of calls from the same +chained call: +

+ +.. _calls-as-tuples: + +A call object is either a tuple of (positional args, keyword args) or +(name, positional args, keyword args) depending on how it was constructed. When +you construct them yourself this isn't particularly interesting, but the call +objects that are in the :attr:Mock.call_args, :attr:Mock.call_args_list and +:attr:Mock.mock_calls attributes can be introspected to get at the individual +arguments they contain. + +The call objects in :attr:Mock.call_args and :attr:Mock.call_args_list +are two-tuples of (positional args, keyword args) whereas the call objects +in :attr:Mock.mock_calls, along with ones you construct yourself, are +three-tuples of (name, positional args, keyword args). + +You can use their "tupleness" to pull out the individual arguments for more +complex introspection and assertions. The positional arguments are a tuple +(an empty tuple if there are no positional arguments) and the keyword +arguments are a dictionary: +

+

+ + +create_autospec +--------------- + +.. function:: create_autospec(spec, spec_set=False, instance=False, **kwargs) +

+

+

+

+

+ +See :ref:auto-speccing for examples of how to use auto-speccing with +create_autospec and the autospec argument to :func:patch. + + +ANY +--- + +.. data:: ANY + +Sometimes you may need to make assertions about some of the arguments in a +call to mock, but either not care about some of the arguments or want to pull +them individually out of :attr:~Mock.call_args and make more complex +assertions on them. + +To ignore certain arguments you can pass in objects that compare equal to +everything. Calls to :meth:~Mock.assert_called_with and +:meth:~Mock.assert_called_once_with will then succeed no matter what was +passed in. +

+ +ANY can also be used in comparisons with call lists like +:attr:~Mock.mock_calls: +

+ + + +FILTER_DIR +---------- + +.. data:: FILTER_DIR + +FILTER_DIR is a module level variable that controls the way mock objects +respond to dir (only for Python 2.6 or more recent). The default is True, +which uses the filtering described below, to only show useful members. If you +dislike this filtering, or need to switch it off for diagnostic purposes, then +set mock.FILTER_DIR = False. + +With filtering on, dir(some_mock) shows only useful attributes and will +include any dynamically created attributes that wouldn't normally be shown. +If the mock was created with a spec (or autospec of course) then all the +attributes from the original are shown, even if they haven't been accessed +yet: +

+ +Many of the not-very-useful (private to Mock rather than the thing being +mocked) underscore and double underscore prefixed attributes have been +filtered from the result of calling dir on a Mock. If you dislike this +behaviour you can switch it off by setting the module level switch +FILTER_DIR: +

+ +Alternatively you can just use vars(my_mock) (instance members) and +dir(type(my_mock)) (type members) to bypass the filtering irrespective of +mock.FILTER_DIR. + + +mock_open +--------- + +.. function:: mock_open(mock=None, read_data=None) +

+

+

+ +Using open as a context manager is a great way to ensure your file handles +are closed properly and is becoming common:: +

+ +The issue is that even if you mock out the call to open it is the +returned object that is used as a context manager (and has __enter__ and +__exit__ called). + +Mocking context managers with a :class:MagicMock is common enough and fiddly +enough that a helper function is useful. +

+ +And for reading files: +

+ + +.. _auto-speccing: + +Autospeccing +------------ + +Autospeccing is based on the existing spec feature of mock. It limits the +api of mocks to the api of an original object (the spec), but it is recursive +(implemented lazily) so that attributes of mocks only have the same api as +the attributes of the spec. In addition mocked functions / methods have the +same call signature as the original so they raise a TypeError if they are +called incorrectly. + +Before I explain how auto-speccing works, here's why it is needed. + +Mock is a very powerful and flexible object, but it suffers from two flaws +when used to mock out objects from a system under test. One of these flaws is +specific to the Mock api and the other is a more general problem with using +mock objects. + +First the problem specific to Mock. Mock has two assert methods that are +extremely handy: :meth:~Mock.assert_called_with and +:meth:~Mock.assert_called_once_with. +

+ +Because mocks auto-create attributes on demand, and allow you to call them +with arbitrary arguments, if you misspell one of these assert methods then +your assertion is gone: + +.. code-block:: pycon +

+ +Your tests can pass silently and incorrectly because of the typo. + +The second issue is more general to mocking. If you refactor some of your +code, rename members and so on, any tests for code that is still using the +old api but uses mocks instead of the real objects will still pass. This +means your tests can all pass even though your code is broken. + +Note that this is another reason why you need integration tests as well as +unit tests. Testing everything in isolation is all fine and dandy, but if you +don't test how your units are "wired together" there is still lots of room +for bugs that tests might have caught. + +mock already provides a feature to help with this, called speccing. If you +use a class or instance as the spec for a mock then you can only access +attributes on the mock that exist on the real class: +

+ +The spec only applies to the mock itself, so we still have the same issue +with any methods on the mock: + +.. code-block:: pycon +

+ +Auto-speccing solves this problem. You can either pass autospec=True to +patch / patch.object or use the create_autospec function to create a +mock with a spec. If you use the autospec=True argument to patch then the +object that is being replaced will be used as the spec object. Because the +speccing is done "lazily" (the spec is created as attributes on the mock are +accessed) you can use it with very complex or deeply nested objects (like +modules that import modules that import modules) without a big performance +hit. + +Here's an example of it in use: +

+ +You can see that request.Request has a spec. request.Request takes two +arguments in the constructor (one of which is self). Here's what happens if +we try to call it incorrectly: +

+ +The spec also applies to instantiated classes (i.e. the return value of +specced mocks): +

+ +Request objects are not callable, so the return value of instantiating our +mocked out request.Request is a non-callable mock. With the spec in place +any typos in our asserts will raise the correct error: +

+ +In many cases you will just be able to add autospec=True to your existing +patch calls and then be protected against bugs due to typos and api +changes. + +As well as using autospec through patch there is a +:func:create_autospec for creating autospecced mocks directly: +

+ +This isn't without caveats and limitations however, which is why it is not +the default behaviour. In order to know what attributes are available on the +spec object, autospec has to introspect (access attributes) the spec. As you +traverse attributes on the mock a corresponding traversal of the original +object is happening under the hood. If any of your specced objects have +properties or descriptors that can trigger code execution then you may not be +able to use autospec. On the other hand it is much better to design your +objects so that introspection is safe [#]_. + +A more serious problem is that it is common for instance attributes to be +created in the __init__ method and not to exist on the class at all. +autospec can't know about any dynamically created attributes and restricts +the api to visible attributes. +

+ +There are a few different ways of resolving this problem. The easiest, but +not necessarily the least annoying, way is to simply set the required +attributes on the mock after creation. Just because autospec doesn't allow +you to fetch attributes that don't exist on the spec it doesn't prevent you +setting them: +

+ +There is a more aggressive version of both spec and autospec that does +prevent you setting non-existent attributes. This is useful if you want to +ensure your code only sets valid attributes too, but obviously it prevents +this particular scenario: +

+ +Probably the best way of solving the problem is to add class attributes as +default values for instance members initialised in __init__. Note that if +you are only setting default attributes in __init__ then providing them via +class attributes (shared between instances of course) is faster too. e.g. + +.. code-block:: python +

+ +This brings up another issue. It is relatively common to provide a default +value of None for members that will later be an object of a different type. +None would be useless as a spec because it wouldn't let you access any +attributes or methods on it. As None is never going to be useful as a +spec, and probably indicates a member that will normally of some other type, +autospec doesn't use a spec for members that are set to None. These will +just be ordinary mocks (well - MagicMocks): +

+ +If modifying your production classes to add defaults isn't to your liking +then there are more options. One of these is simply to use an instance as the +spec rather than the class. The other is to create a subclass of the +production class and add the defaults to the subclass without affecting the +production class. Both of these require you to use an alternative object as +the spec. Thankfully patch supports this - you can simply pass the +alternative object as the autospec argument: +

+ + +.. [#] This only applies to classes or already instantiated objects. Calling

new file mode 100644 --- /dev/null +++ b/Doc/library/unittest.mock-magicmethods.rst @@ -0,0 +1,226 @@ +:mod:unittest.mock --- MagicMock and magic method support +=========================================================== + +.. module:: unittest.mock

+.. versionadded:: 3.3 + + +.. magic-methods: + +Mocking Magic Methods +--------------------- + +:class:Mock supports mocking the Python protocol methods, also known as +"magic methods". This allows mock objects to replace containers or other +objects that implement Python protocols. + +Because magic methods are looked up differently from normal methods [#], this +support has been specially implemented. This means that only specific magic +methods are supported. The supported list includes almost all of them. If +there are any missing that you need please let us know. + +You mock magic methods by setting the method you are interested in to a function +or a mock instance. If you are using a function then it must take self as +the first argument [#]_. +

+One use case for this is for mocking objects used as context managers in a +with statement: +

+Calls to magic methods do not appear in :attr:~Mock.method_calls, but they +are recorded in :attr:~Mock.mock_calls. + +.. note:: +

+The full list of supported magic methods is: + +* __hash__, __sizeof__, __repr__ and __str__ +* __dir__, __format__ and __subclasses__ +* __floor__, __trunc__ and __ceil__ +* Comparisons: __cmp__, __lt__, __gt__, __le__, __ge__,

+ +.. class:: NonCallableMagicMock(*args, **kw) +

+

+ +The magic methods are setup with MagicMock objects, so you can configure them +and use them in the usual way: +

+By default many of the protocol methods are required to return objects of a +specific type. These methods are preconfigured with a default return value, so +that they can be used without you having to do anything if you aren't interested +in the return value. You can still set the return value manually if you want +to change the default. + +Methods and their defaults: + +* __lt__: NotImplemented +* __gt__: NotImplemented +* __le__: NotImplemented +* __ge__: NotImplemented +* __int__ : 1 +* __contains__ : False +* __len__ : 1 +* __iter__ : iter([]) +* __exit__ : False +* __complex__ : 1j +* __float__ : 1.0 +* __bool__ : True +* __index__ : 1 +* __hash__ : default hash for the mock +* __str__ : default str for the mock +* __sizeof__: default sizeof for the mock + +For example: +

+The two equality method, __eq__ and __ne__, are special. +They do the default equality comparison on identity, using a side +effect, unless you change their return value to return something else: +

+The return value of MagicMock.__iter__ can be any iterable object and isn't +required to be an iterator: +

+If the return value is an iterator, then iterating over it once will consume +it and subsequent iterations will result in an empty list: +

+MagicMock has all of the supported magic methods configured except for some +of the obscure and obsolete ones. You can still set these up if you want. + +Magic methods that are supported but not setup by default in MagicMock are: + +* __subclasses__ +* __dir__ +* __format__ +* __get__, __set__ and __delete__ +* __reversed__ and __missing__ +* __reduce__, __reduce_ex__, __getinitargs__, __getnewargs__,

new file mode 100644 --- /dev/null +++ b/Doc/library/unittest.mock-patch.rst @@ -0,0 +1,538 @@ +:mod:unittest.mock --- the patchers +===================================== + +.. module:: unittest.mock

+.. versionadded:: 3.3 + +The patch decorators are used for patching objects only within the scope of +the function they decorate. They automatically handle the unpatching for you, +even if exceptions are raised. All of these functions can also be used in with +statements or as class decorators. + + +patch +----- + +.. note:: +

+ +.. function:: patch(target, new=DEFAULT, spec=None, create=False, spec_set=None, autospec=None, new_callable=None, **kwargs) +

+

+

+

+

+

+

+

+

+

+

+

+

+ + +Patching a class replaces the class with a MagicMock instance. If the +class is instantiated in the code under test then it will be the +:attr:~Mock.return_value of the mock that will be used. + +If the class is instantiated multiple times you could use +:attr:~Mock.side_effect to return a new mock each time. Alternatively you +can set the return_value to be anything you want. + +To configure return values on methods of instances on the patched class +you must do this on the return_value. For example: +

+ +If you use spec or spec_set and patch is replacing a class, then the +return value of the created mock will have the same spec. +

+ +The new_callable argument is useful where you want to use an alternative +class to the default :class:MagicMock for the created mock. For example, if +you wanted a :class:NonCallableMock to be used: +

+ +Another use case might be to replace an object with a StringIO instance: +

+ +When patch is creating a mock for you, it is common that the first thing +you need to do is to configure the mock. Some of that configuration can be done +in the call to patch. Any arbitrary keywords you pass into the call will be +used to set attributes on the created mock: +

+ +As well as attributes on the created mock attributes, like the +:attr:~Mock.return_value and :attr:~Mock.side_effect, of child mocks can +also be configured. These aren't syntactically valid to pass in directly as +keyword arguments, but a dictionary with these as keys can still be expanded +into a patch call using **: +

+ + +patch.object +------------ + +.. function:: patch.object(target, attribute, new=DEFAULT, spec=None, create=False, spec_set=None, autospec=None, new_callable=None, **kwargs) +

+

+

+ +You can either call patch.object with three arguments or two arguments. The +three argument form takes the object to be patched, the attribute name and the +object to replace the attribute with. + +When calling with the two argument form you omit the replacement object, and a +mock is created for you and passed in as an extra argument to the decorated +function: +

+ +spec, create and the other arguments to patch.object have the same +meaning as they do for patch. + + +patch.dict +---------- + +.. function:: patch.dict(in_dict, values=(), clear=False, **kwargs) +

+

+

+

+

+

+

+ +patch.dict can be used to add members to a dictionary, or simply let a test +change a dictionary, and ensure the dictionary is restored when the test +ends. +

+

+ +Keywords can be used in the patch.dict call to set values in the dictionary: +

+ +patch.dict can be used with dictionary like objects that aren't actually +dictionaries. At the very minimum they must support item getting, setting, +deleting and either iteration or membership test. This corresponds to the +magic methods __getitem__, __setitem__, __delitem__ and either +__iter__ or __contains__. +

+ + +patch.multiple +-------------- + +.. function:: patch.multiple(target, spec=None, create=False, spec_set=None, autospec=None, new_callable=None, **kwargs) +

+

+

+

+

+ +If you want patch.multiple to create mocks for you, then you can use +:data:DEFAULT as the value. If you use patch.multiple as a decorator +then the created mocks are passed into the decorated function by keyword. +

+

+ +patch.multiple can be nested with other patch decorators, but put arguments +passed by keyword after any of the standard arguments created by patch: +

+ +If patch.multiple is used as a context manager, the value returned by the +context manger is a dictionary where created mocks are keyed by name: +

+ + +.. _start-and-stop: + +patch methods: start and stop +----------------------------- + +All the patchers have start and stop methods. These make it simpler to do +patching in setUp methods or where you want to do multiple patches without +nesting decorators or with statements. + +To use them call patch, patch.object or patch.dict as normal and keep a +reference to the returned patcher object. You can then call start to put +the patch in place and stop to undo it. + +If you are using patch to create a mock for you then it will be returned by +the call to patcher.start. +

+ + +A typical use case for this might be for doing multiple patches in the setUp +method of a TestCase: +

+ +.. caution:: +

+

+

+ +In fact start and stop are just aliases for the context manager +__enter__ and __exit__ methods. + + +TEST_PREFIX +----------- + +All of the patchers can be used as class decorators. When used in this way +they wrap every test method on the class. The patchers recognise methods that +start with test as being test methods. This is the same way that the +:class:unittest.TestLoader finds test methods by default. + +It is possible that you want to use a different prefix for your tests. You can +inform the patchers of the different prefix by setting patch.TEST_PREFIX: +

+ + +Nesting Patch Decorators +------------------------ + +If you want to perform multiple patches then you can simply stack up the +decorators. + +You can stack up multiple patch decorators using this pattern: +

+ + +Note that the decorators are applied from the bottom upwards. This is the +standard way that Python applies decorators. The order of the created mocks +passed into your test function matches this order. + + +.. _where-to-patch: + +Where to patch +-------------- + +patch works by (temporarily) changing the object that a name points to with +another one. There can be many names pointing to any individual object, so +for patching to work you must ensure that you patch the name used by the system +under test. + +The basic principle is that you patch where an object is looked up, which +is not necessarily the same place as where it is defined. A couple of +examples will help to clarify this. + +Imagine we have a project that we want to test with the following structure:: +

+

+ +Now we want to test some_function but we want to mock out SomeClass using +patch. The problem is that when we import module b, which we will have to +do then it imports SomeClass from module a. If we use patch to mock out +a.SomeClass then it will have no effect on our test; module b already has a +reference to the real SomeClass and it looks like our patching had no +effect. + +The key is to patch out SomeClass where it is used (or where it is looked up +). In this case some_function will actually look up SomeClass in module b, +where we have imported it. The patching should look like:: +

+ +However, consider the alternative scenario where instead of from a import[](#l6.527) +SomeClass module b does import a and some_function uses a.SomeClass. Both +of these import forms are common. In this case the class we want to patch is +being looked up on the a module and so we have to patch a.SomeClass instead:: +

+ + +Patching Descriptors and Proxy Objects +-------------------------------------- + +Both patch_ and patch.object_ correctly patch and restore descriptors: class +methods, static methods and properties. You should patch these on the class +rather than an instance. They also work with some objects +that proxy attribute access, like the django setttings object[](#l6.541) +<http://www.voidspace.org.uk/python/weblog/arch_d7_2010_12_04.shtml#e1198>_.

new file mode 100644 --- /dev/null +++ b/Doc/library/unittest.mock.rst @@ -0,0 +1,900 @@ +:mod:unittest.mock --- mock object library +============================================ + +.. module:: unittest.mock

+.. versionadded:: 3.3 + +:mod:unittest.mock is a library for testing in Python. It allows you to +replace parts of your system under test with mock objects and make assertions +about how they have been used. + +unittest.mock provides a core :class:Mock class removing the need to +create a host of stubs throughout your test suite. After performing an +action, you can make assertions about which methods / attributes were used +and arguments they were called with. You can also specify return values and +set needed attributes in the normal way. + +Additionally, mock provides a :func:patch decorator that handles patching +module and class level attributes within the scope of a test, along with +:const:sentinel for creating unique objects. See the quick guide_ for +some examples of how to use :class:Mock, :class:MagicMock and +:func:patch. + +Mock is very easy to use and is designed for use with :mod:unittest. Mock +is based on the 'action -> assertion' pattern instead of 'record -> replay' +used by many mocking frameworks. + +There is a backport of unittest.mock for earlier versions of Python, +available as mock on PyPI <http://pypi.python.org/pypi/mock>_. + +Source code: :source:Lib/unittest/mock.py + + +Quick Guide +----------- + +:class:Mock and :class:MagicMock objects create all attributes and +methods as you access them and store details of how they have been used. You +can configure them, to specify return values or limit what attributes are +available, and then make assertions about how they have been used: +

+ +:attr:side_effect allows you to perform side effects, including raising an +exception when a mock is called: +

+Mock has many other ways you can configure it and control its behaviour. For +example the spec argument configures the mock to take its specification +from another object. Attempting to access attributes or methods on the mock +that don't exist on the spec will fail with an AttributeError. + +The :func:patch decorator / context manager makes it easy to mock classes or +objects in a module under test. The object you specify will be replaced with a +mock (or other object) during the test and restored when the test ends: +

+

+ +.. note:: +

+As well as a decorator patch can be used as a context manager in a with +statement: +

+ + +There is also :func:patch.dict for setting values in a dictionary just +during a scope and restoring the dictionary to its original state when the test +ends: +

+Mock supports the mocking of Python :ref:magic methods <magic-methods>. The +easiest way of using magic methods is with the :class:MagicMock class. It +allows you to do things like: +

+ +Mock allows you to assign functions (or other Mock instances) to magic methods +and they will be called appropriately. The MagicMock class is just a Mock +variant that has all of the magic methods pre-created for you (well, all the +useful ones anyway). + +The following is an example of using magic methods with the ordinary Mock +class: +

+ +For ensuring that the mock objects in your tests have the same api as the +objects they are replacing, you can use :ref:auto-speccing <auto-speccing>. +Auto-speccing can be done through the autospec argument to patch, or the +:func:create_autospec function. Auto-speccing creates mock objects that +have the same attributes and methods as the objects they are replacing, and +any functions and methods (including constructors) have the same call +signature as the real object. + +This ensures that your mocks will fail in the same way as your production +code if they are used incorrectly: +

+create_autospec can also be used on classes, where it copies the signature of +the __init__ method, and on callable objects where it copies the signature of +the __call__ method. + + + +The Mock Class +-------------- + + +Mock is a flexible mock object intended to replace the use of stubs and +test doubles throughout your code. Mocks are callable and create attributes as +new mocks when you access them [#]_. Accessing the same attribute will always +return the same mock. Mocks record how you use them, allowing you to make +assertions about what your code has done to them. + +:class:MagicMock is a subclass of Mock with all the magic methods +pre-created and ready to use. There are also non-callable variants, useful +when you are mocking out objects that aren't callable: +:class:NonCallableMock and :class:NonCallableMagicMock + +The :func:patch decorators makes it easy to temporarily replace classes +in a particular module with a Mock object. By default patch will create +a MagicMock for you. You can specify an alternative class of Mock using +the new_callable argument to patch. + + +.. class:: Mock(spec=None, side_effect=None, return_value=DEFAULT, wraps=None, name=None, spec_set=None, **kwargs) +

+

+

+

+

+

+

+

+

+

+

+

+

+ +

+

+

+ +

+

+

+ +

+

+

+

+ +

+

+

+

+

+ +

+

+

+

+ +

+

+

+ +

+

+ +

+

+

+

+

+

+

+ +

+

+

+ +

+

+

+ +

+

+

+

+

+

+ +

+

+

+

+

+

+

+ +

+

+

+

+

+

+

+

+

+

+

+

+

+ +

+

+

+

+ +

+

+

+

+ +

+

+

+

+ +

+

+

+

+ +

+

+

+

+

+ +.. class:: NonCallableMock(spec=None, wraps=None, name=None, spec_set=None, **kwargs) +

+ +Mock objects that use a class or an instance as a spec or spec_set are able +to pass isintance tests: +

+ +The Mock classes have support for mocking magic methods. See :ref:magic[](#l7.663) +methods <magic-methods> for the full details. + +The mock classes and the :func:patch decorators all take arbitrary keyword +arguments for configuration. For the patch decorators the keywords are +passed to the constructor of the mock being created. The keyword arguments +are for configuring attributes of the mock: +

+ +The return value and side effect of child mocks can be set in the same way, +using dotted notation. As you can't use dotted names directly in a call you +have to create a dictionary and unpack it using **: +

+ + +.. class:: PropertyMock(*args, **kwargs) +

+ + +Calling +~~~~~~~ + +Mock objects are callable. The call will return the value set as the +:attr:~Mock.return_value attribute. The default return value is a new Mock +object; it is created the first time the return value is accessed (either +explicitly or by calling the Mock) - but it is stored and the same one +returned each time. + +Calls made to the object will be recorded in the attributes +like :attr:~Mock.call_args and :attr:~Mock.call_args_list. + +If :attr:~Mock.side_effect is set then it will be called after the call has +been recorded, so if side_effect raises an exception the call is still +recorded. + +The simplest way to make a mock raise an exception when called is to make +:attr:~Mock.side_effect an exception class or instance: +

+ +If side_effect is a function then whatever that function returns is what +calls to the mock return. The side_effect function is called with the +same arguments as the mock. This allows you to vary the return value of the +call dynamically, based on the input: +

+ +If you want the mock to still return the default return value (a new mock), or +any set return value, then there are two ways of doing this. Either return +mock.return_value from inside side_effect, or return :data:DEFAULT: +

+ +To remove a side_effect, and return to the default behaviour, set the +side_effect to None: +

+ +The side_effect can also be any iterable object. Repeated calls to the mock +will return values from the iterable (until the iterable is exhausted and +a StopIteration is raised): +

+ + +.. _deleting-attributes: + +Deleting Attributes +~~~~~~~~~~~~~~~~~~~ + +Mock objects create attributes on demand. This allows them to pretend to be +objects of any type. + +You may want a mock object to return False to a hasattr call, or raise an +AttributeError when an attribute is fetched. You can do this by providing +an object as a spec for a mock, but that isn't always convenient. + +You "block" attributes by deleting them. Once deleted, accessing an attribute +will raise an AttributeError. +

+ + +Attaching Mocks as Attributes +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +When you attach a mock as an attribute of another mock (or as the return +value) it becomes a "child" of that mock. Calls to the child are recorded in +the :attr:~Mock.method_calls and :attr:~Mock.mock_calls attributes of the +parent. This is useful for configuring child mocks and then attaching them to +the parent, or for attaching mocks to a parent that records all calls to the +children and allows you to make assertions about the order of calls between +mocks: +

+ +The exception to this is if the mock has a name. This allows you to prevent +the "parenting" if for some reason you don't want it to happen. +

+ +Mocks created for you by :func:patch are automatically given names. To +attach mocks that have names to a parent you use the :meth:~Mock.attach_mock +method: +

+ + +.. [#] The only exceptions are magic methods and attributes (those that have

--- a/Lib/unittest/mock.py +++ b/Lib/unittest/mock.py @@ -1577,11 +1577,9 @@ right = ' '.join('r%s' % n for n in nume

del is not supported at all as it causes problems if it exists

non_defaults = set('_%s' % method for method in [

])