Reputation: 1398
I'm trying to mock a self method using pytest-mock.
Simply my class got a function "distance" which I want to mock.
I want to test my eq function that is like this:
def __eq__(self, other):
return self.distance() == other.distance()
I try something like this:
def test_eq(mocker):
i = mocker.MagicMock(Interval)
mocker.patch.object(i, 'distance', return_value=1)
i2 = mocker.MagicMock(Interval)
mocker.patch.object(i2, 'distance', return_value=1)
assert i == i2
But this return:
AssertionError: assert <\MagicMock spec='Interval' id='140333310434384'> ==<\MagicMock spec='Interval' id='140333310558104'>
I have also tried
mocker.patch.object(i, 'self.distance', return_value=1)
but this get me an AttributeError as i expected from MagicMock.
What is the right way to patch my object self method?
Upvotes: 1
Views: 2373
Reputation: 535
You can easily mock out the distance method like this.
Assuming that your Interval
class is defined in the interval module for example like this:
class Interval:
def __eq__(self, other):
return self.distance() == other.distance()
def distance(self):
raise NotImplementedError()
Then in your test you can just mock out the distance function to always return 1 like this:
from interval import Interval
def test_eq(mocker):
mocker.patch('interval.Interval.distance', return_value=1)
i1 = Interval()
i2 = Interval()
assert i1 == i2
Upvotes: 0
Reputation: 530
I don't think you can patch 'Interval' like this. Instead you should patch the constructor and manually replace the distance functions to return expected results.
This example will only test the Interval.__eq__
method:
def test_eq(mocker):
# Mock constructor as it is already tested elsewhere
mocker.patch.object(Interval, "__init__", return_value=None)
i1 = Interval()
i1.distance = lambda: 1
i2 = Interval()
i2.distance = lambda: 1
assert i1 == i2
Upvotes: 0