I've looked up everywhere and got no definite response to a rather trivial question.
I have a Python project in PyCharm on Windows 7 that contains multiple .py
files (which are connected via "from %package_name%.%script_name% import %class_name%
") and a folder inside the project with two simple text files. I've installed PyInstaller 3.6 into project's venv
and use it as an external tool, that points to a .spec
file. So far, so good. The .spec
file is as follows:
# -*- mode: python ; coding: utf-8 -*-
block_cipher = None
a = Analysis(['C:\\Users\\%username%\\PycharmProjects\\%project_folder%\\%project_folder%\\main.py'],
pathex=['C:\\Users\\%username%\\PycharmProjects\\%project_folder%\\%project_folder%'],
binaries=[],
datas=[('txt_files\\file1.txt', '.'), ('txt_files\\file2.txt', '.')],
hiddenimports=[],
hookspath=[],
runtime_hooks=[],
excludes=[],
win_no_prefer_redirects=False,
win_private_assemblies=False,
cipher=block_cipher,
noarchive=False)
a.datas += [
("C:\\Users\\%username%\\PycharmProjects\\%project_folder%\\%project_folder%\\txt_files\\file1.txt","txt_files\\file1.txt","DATA"),
("C:\\Users\\%username%\\PycharmProjects\\%project_folder%\\%project_folder%\\txt_files\\file2.txt","txt_files\\file2.txt","DATA"),
]
pyz = PYZ(a.pure, a.zipped_data,
cipher=block_cipher)
exe = EXE(pyz,
a.scripts,
[],
exclude_binaries=True,
name='%project_name%',
debug=False,
bootloader_ignore_signals=False,
strip=False,
upx=True,
console=True )
coll = COLLECT(exe,
a.binaries,
a.zipfiles,
a.datas,
strip=False,
upx=True,
upx_exclude=[],
name='%project_name%')
The problem is that if I hard-code the absolute paths to the bundled .txt
files in the scripts themselves, the app compiles and has no run-time errors. However, if I use relative paths inside the scripts, the app compiles, but gives a run-time error, that a .txt
file (i.e. file1.txt
) is not found INSIDE the /build
(or /dist
, I may be wrong here) directory (which is obviously not there).
Of course, hard-coding the absolute paths is a bad practice, especially, when talking not only about portability to another machine, but also making the app cross-platform. I know that the build process may depend on sys._MEIPASS
, but I don't know exactly how to use it in my context.
In which script (main
, .spec
or other?) shall I put the part that gets the absolute path to a bundled file using sys._MEIPASS
? And how should this code part look like on Python 3.7? I've seen different answers (i.e. this one) and already tried them, but none seemed to work in my case.