Search code examples
pythonpython-3.xunit-testingpython-unittest

how to get python unit test overwrite variable from imported package


Trying to figure out how to overwrite a variable during unit testing:

#mainscript.py
import json

org_file = 'unitfile.json'

def load_json (file_name):
    with open ('{0}'.format(org_file)) as f:
       json_object =  json.load(f)
    return json_object

new_file = load_json(org_file)

def print_me():
    return (new_file['text'])

def main():
    print_me()

if __name__ == '__main__':
    main()

Unit test:

#test_mainscript.py
import json
import mainscript
import unittest
from  unittest.mock import patch

class Testmainscript(unittest.TestCase):
    # def setUp(self):
        # Not needed when using mock
    @patch('mainscript.org_file','unitfile2.json')
    def test_print_me(self):
        self.assertEqual(mainscript.org_file, 'unitfile2.json') # Correctly overwrites file
        self.assertEqual(mainscript.print_me(),'Bye World') #does not pass, still reading unitfile.json instead of unitfile2.json
if __name__ == '__main__':
    unittest.main()

This test should fail because because I'm overwriting org_file with unitestfile2.json (which contains {'text':'Bye World'}) instead of unittestfile.json (which contains {'text':'Hello World'})

But its currently passing because the variable isn't being overwritten


Solution

  • What you are looking for is called "mocking", an example for your case:

    import json
    import mainscript
    import unittest
    from unittest.mock import patch
    
    class Testmainscript(unittest.TestCase):
        # def setUp(self):
            # Not needed when using mock
     
        @patch('mainscript.org_file', 'unitfile2.json')
        def test_print_me(self):
            self.assertEqual(mainscript.print_me(),'Hello World')
    
    if __name__ == '__main__':
        unittest.main()