I'm new to Python so forgive me if this is basic. I have a method under test and in that method, I instantiate an object and call methods on it and want to test that those are called correctly (worth pointing out that this code is pre-existing and I'm merely adding to it, with no existing tests).
Method under test
def dispatch_events(event):
dispatcher = Dispatcher()
dispatcher.register("TopicOne")
dispatcher.push(event)
Expected test
# Some patch here
def test_dispatch_events(self, mock_dispatcher):
# Given
event = { "some_prop": "some_value" }
# When
Class.dispatch_events(event)
# Then
mock_dispatcher.register.assert_called_once_with("TopicOne")
mock_dispatcher.push.assert_called_once_with(event)
Coming from a .NET background my immediate thought is to pass Dispatcher
into dispatch_events
as a parameter. Then presumably, I can pass in a MagicMock
version. Or I thought that you might be able to patch the __init__
method on the Dispatcher
and return a MagicMock
. Before I continue with this I wanted to know whether a) it's possible and b) what's the best practice for testing this (fully accepting that writing a better method might be that best practice).
Make dispatcher
an argument, and you don't need to patch anything.
def dispatch_events(event, dispatcher=None):
if dispatcher is None:
dispatcher = Dispatcher()
dispatcher.register("TopicOne")
dispatcher.push(event)
def test_dispatch_events(self):
event = {"some_prop": "some_value"}
mock_dispatcher = Mock()
Class.dispatch_events(event, mock_dispatcher)
mock_dispatcher.register.assert_called_once_with("TopicOne")
mock_dispatcher.push.assert_called_once_with(event)
If that's not an option, the correct thing to mock in most cases will be Dispatcher.__new__
or some.module.Dispatcher
itself.
# The exact value of 'some.module' depends on how the module that
# defines dispatch_events gets access to Dispatcher.
@mock.patch('some.module.Dispatcher')
def test_dispatch_events(self, mock_dispatcher):
event = {"some_prop": "some_value"}
Class.dispatch_events(event)
mock_dispatcher.register.assert_called_once_with("TopicOne")
mock_dispatcher.push.assert_called_once_with(event)