Search code examples
pythonunit-testingpycharmmayapython-unittest

How to run pycharm unittests when standard lib is zipped?


I've been trying to port a Maya based python project over to PyCharm but I'm having trouble running unit tests.

Maya provides its own python interpreter (mayapy.exe) with a zipped version of the python stdlib (in this case, 'Python27.zip') AFAIK there's nothing special about the stdlib here, but to run the native maya functions you have to use MayaPy rather than a generic python.

The problem appears to be that the jetBrains test runner (utRunner.py) wants to get os.system and it's barfing because it uses a specific import routine that doesn't allow for zip files. It tries this:

def import_system_module(name):
  if sys.platform == "cli":    # hack for the ironpython
      return __import__(name)
  f, filename, desc = imp.find_module(name)
  return imp.load_module('pycharm_' + name, f, filename, desc)

and fails with this error:

 ImportError: No module named os

I think because this is bypassing the zip import hook.

There's one solution posted here, which is basically to unzip the standard library zip. I'm reluctant to do that because I might need to run the tests on machines where I don't have admin rights. I'm also reluctant to patch the code above since I'm not clear how it fits in to the whole test process.

So: how to run tests with a zipped standardlib using PyCharm, without unzipping the library or tweaking the PyCharm install too much?


Solution

  • For lurkers: I was unable to find a better solution than the one linked above, so it was necessary to unzip the 2.7 standard libary into a loose folder. Inelegant, but it works,.

    There was a further wrinkle that maya users need to watch out for: PyCharm does not like tests which run Maya.standalone -- the standalone session did not exit properly, so when running tests (in onr ore more files) that called

     import maya.standalone
     maya.standalone.initialize()
    

    The pycharm test runner would hang on completion. After much frustration I found that adding an atexit handler to the test code would allow the standalone to exit in a way that PyCharm could tolerate:

    def get_out_of_maya():
        try:
           import maya.commands as cmds
           cmds.file(new=True, force=True)
        except:
           pass
        os._exit(0)   # note underscore
    
    import atexit
    atexit.register(get_out_of_maya)
    

    This pre-empts the atexit hook in Maya and allows the tests to complete to the satisfaction of the Pycharm runner. FWIW, it also helps if you are running MayaPy.exe from a subprocess and executing your tests that way.