I am creating a package to be used in our company that adds the root of the project to the system path.
I will add a source_root.config
file in our root directory.
add_root_path.py
import sys
import inspect
from pathlib import Path
from inspect import getsourcefile
CUR_FILE = Path(getsourcefile(lambda:0)).name
SOURCE_ROOT_DEFAULT_FILE = 'source_root.config'
def _get_dir_of_importer_file():
""" the directory of the file importing the package"""
frames_stack = inspect.stack()
for frame in frames_stack:
# first file that's not importlib._bootstrap and not current file
if 'py' in frame.filename and Path(frame.filename).name != CUR_FILE:
file_name = frame.filename
break
return Path(file_name).resolve().parent
def find_source_root(source_root_file=SOURCE_ROOT_DEFAULT_FILE):
importer_dir = _get_dir_of_importer_file()
while True: # can go wrong if package is not used correctly
files_in_dir = map(Path.resolve, importer_dir.glob('*'))
for file in files_in_dir:
if file.name == source_root_file:
return importer_dir
importer_dir = importer_dir.parent
def append_root_to_path(source_root_file=SOURCE_ROOT_DEFAULT_FILE):
source_root = find_source_root(source_root_file)
sys.path.append(source_root.resolve().as_posix())
This is done in order to properly import the files inside the project and because using PYTHONPATH
in windows is not that convenient for pytest
and alembic
(meaning not running the files directly via python.exe
).