1

I am trying unit test in Python.

test.py

from unittest import TestCase,main
from unittest.mock import patch

import file

def mock_return(*args):
    return -1

class Tests(TestCase):
    @patch("file.Foo.a", side_effect=mock_return)
    def test_1(self, mock_fun):
        self.assertEqual(file.Foo().a(), -1)

    @patch("os.urandom", side_effect=mock_return)
    def test_2(self, mock_fun):
        self.assertEqual(file.Foo().b(), -1)

if __name__ == "__main__":
    main()

file.py

from os import urandom

class Foo:
    def a(self):
        return 1

    def b(self):
        return urandom(1)

Why test_1 passed but test_2 failed? Is there a way to mock a method used by other class?

1 Answer 1

1

You must patch the binding used by the function being tested.

from os import urandom  # in file.py

binds name urandom to the function os.urandom in the file module. Foo.b accesses the function via the file.urandom binding. So the test for Foo.b must patch file.urandom, not os.urandom.

Sign up to request clarification or add additional context in comments.

2 Comments

This is the answer I need. from os import urandom needs file.urandom and import os need os.urandom
I was thinking of changing @patch("os.urandom",... to @patch("file.urandom",..., and both test pass after that. An alternative is to change from os import urandom to import os and change the call in Foo.b to os.urandom. I personally prefer the former as I prefer doing the patching in the tested code, rather than the stdlib. But the important point is that the test, including mocking, must carefully match the tested code.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.