When using PyInstaller to package an application to a self-containing bundle you might run into some pitfalls:
Table of Contents
Pitfall 1: PyInstaller overwrites spec file
The first time you run pyinstaller you run it with
pyi-makespec my_module.py
instead of
pyinstaller my_module.py
pyi-makespec will generate a my_module.spec which you can alter. Afterwards you just ran
pyinstaller my_module.spec
to avoid overwriting the spec file.
Pitfall 2: Packing additional resources
If You want to have additional files in your distribution you can alter the .spec file:
a = Analysis(['my_module.py'], pathex=['C:\\Users\\jrb\\PycharmProjects\\pyinstaller_test'], binaries=[], datas=[("docs/user_manual.txt", ".")],
Pitfall 3: Templates not found after packaging
If you are using for example a templating engine like jinja2 and have to access the templates from the distribution you have to fiddle with the path:
path = os.getcwd() if getattr(sys, 'frozen', False): logger.debug("We are running in a bundle!") path = getattr(sys, '_MEIPASS', os.getcwd()) logger.debug("Bundle path" + path) file_loader = FileSystemLoader(os.path.join(path, 'templates')) env = Environment(loader=file_loader) template = env.get_template('template.html')
Pitfall 4: Running PyInstaller from an virtual environment
When running PyInstaller from inside a virtual environment you sometimes get
File "C:\Python37\lib\ntpath.py", line 183, in split p = os.fspath(p) TypeError: expected str, bytes or os.PathLike object, not NoneType
In that case you can pactch venv/Lib/site-packages/PyInstaller/depend/bindepend.py with the following snippet:
# Work around for python venv having VERSION.dll rather than pythonXY.dll if is_win and 'VERSION.dll' in dlls: pydll = 'python%d%d.dll' % sys.version_info[:2] if pydll in PYDYLIB_NAMES: filename = getfullnameof(pydll) return filename
Pitfall 5: Making a single file executable
When You want to get a single file executable you can use the -F flag (or –onefile) for generating the .spec-file. This works only when you have no additional data which should be copied 🙂
pyi-makespec -F my_module.py
Pitfall 6: ModuleNotFoundError: No module named ‘_socket’
I’ve ran into a diverse set of issues where modules weren’t found.
Packaged programs seem to be unable to run from network drives directly.
It is always a good idea to also clean the cashes
on Windows: %APPDATA%\pyinstaller (or ~\Application Data\pyinstaller)
Troubleshooting guide
https://github.com/pyinstaller/pyinstaller/wiki/How-to-Report-Bugs