How to use python Mock side_effect to act as a class method in unit test

I am testing a user API in python that handles HTTP requests, but I do not want to make a request to a real external system every time I run unit tests. I am using the python mock library with side_effect function to dynamically fake an API response. How to make the side_effect method behave like a class method?

import requests class MyApiClass(): def make_request(self, params): return requests.get('http://someurl.com', params=params) def create_an_object(self, params): return self.make_request(params) 

 import unittest, mock def side_effect_func(self, params): if params['name'] == 'Specific Name': return {'text': 'Specific Action'} else: return {'text': 'General Action'} class MyApiTest(unittest.TestCase): def setUp(self): super(MyApiTest, self).setUp() mocked_method = mock.Mock(side_effect=side_effect_func) MyApiClass.make_request = mocked_method def test_create_object(self): api = MyApiClass() params = {'name': 'Specific Name'} r = api.create_an_object(params) # Complains that two arguments are needed! self.assertEqual(r['text'], 'Specific Action') 

I get this error

 TypeError: side_effect_func() takes exactly 2 arguments (1 given) 

but I want side_effect_func pass api as the first argument. Appreciate any help!

+6
source share
1 answer

The easiest way, probably, is to simply make your mock method one argument and then set MyApiClass statically inside the mock method itself. Otherwise, you can try to scoff at the class object itself (basically, make a metaclass layout) or, possibly, using the factory, which uses partial to create the class layout method on the fly. But if one argument / static link method works for you, this seems to me the best.

In addition, from the docs, Mock makes fun of an unrelated method with a patch that looks like it might be more than what you need.

+4
source

Source: https://habr.com/ru/post/957042/


All Articles