unit testing – Mocking Functions Using Python Mock

unit testing – Mocking Functions Using Python Mock

I think I have a workaround, though its still not quite clear on how to solve the general case

In mymodule, if I replace

from util import get_content

class MyObj:    
    def func():
        get_content()

with

import util

class MyObj:    
    def func():
        util.get_content()

The Mock seems to get invoked. It looks like the namespaces need to match (which makes sense). However, the weird thing is that I would expect

import mymodule
mymodule.get_content = mock.Mock(return_value=mocked stuff)

to do the trick in the original case where I am using the from/import syntax (which now pulls in get_content into mymodule). But this still refers to the unmocked get_content.

Turns out the namespace matters – just need to keep that in mind when writing your code.

The general case would be to use patch from mock. Consider the following:

utils.py

def get_content():
    return stuff

mymodule.py

from util import get_content


class MyClass(object):

    def func(self):
        return get_content()

test.py

import unittest

from mock import patch

from mymodule import MyClass

class Test(unittest.TestCase):

    @patch(mymodule.get_content)
    def test_func(self, get_content_mock):
        get_content_mock.return_value = mocked stuff

        my_class = MyClass()
        self.assertEqual(my_class.func(), mocked stuff)
        self.assertEqual(get_content_mock.call_count, 1)
        get_content_mock.assert_called_once()

Note how get_content is mocked, it is not util.get_content, rather mymodule.get_content since we are using it in mymodule.

Above has been tested with mock v2.0.0, nosetests v1.3.7 and python v2.7.9.

unit testing – Mocking Functions Using Python Mock

You have to patch the function where it is being used. In your case that would be in the mymodule module.

import mymodule
>>> mymodule.get_content = Mock(return_value=mocked stuff)
>>> m = mymodule.MyObj()
>>> m.func()
mocked stuff

There is a reference in the docs here: http://docs.python.org/dev/library/unittest.mock.html#where-to-patch

Leave a Reply

Your email address will not be published.