Search code examples
pythonnosetests

Why mocking is still effective after existing a code in nosetests multiple tests?


I have the following code test_A.py which mocks MyClass.mymethod:

from unittest import main
from mocker import Mocker, MockerTestCase
Class test_A(MockerTestCase):
  def setUp(self):
    self.m=Mock()
    MyClass.mymethod = self.m.mock()
    self.m.result(None)
    self.m.count(0,None)
    self.m.replay()

  def test_me(self):
    #Do something about MyClass.method

  def tearDown(self):
    self.m.restore()
    self.m.verify()

I also have another code test_B.py which DOES NOT mock MyClass.mymethod:

Class test_B(MockerTestCase):
  def setUp(self):
    pass

  def test_me(self):
    #Do something about MyClass.method

  def tearDown(self):
     pass

However, when I do "nosetests test_A.py test_B.py", it looks like after testing test_A.py and entering test_B.py, MyClass.mymethod is still mocked up. Not sure why and how to get around it. Thanks!


Solution

  • The line:

    MyClass.mymethod = self.m.mock()
    

    really does replace MyClass.mymethod() with a new object. All subsequent references to MyClass.mymethod will be to the mock object, even if those references are in a different class.

    What you want is a way to replace MyClass.mymethod() that only works in class test_A. The simplest way to achieve this would be to restore the original mymethod in your tearDown method:

    Class test_A():
        def setUp(self):
            self.originalMyMethod = MyClass.mymethod
            self.m=Mock()
            MyClass.mymethod = self.m.mock()
            self.m.result(None)
            self.m.count(0,None)
            self.m.replay()
    
        def test_me(self):
            # Do something about MyClass.mymethod
    
        def tearDown(self):
            self.m.restore()
            self.m.verify()
            MyClass.mymethod = self.originalMyMethod