diff --git a/districtgenerator/classes/certificate_generator.py b/districtgenerator/classes/certificate_generator.py index 4ec43390..5a504e4f 100644 --- a/districtgenerator/classes/certificate_generator.py +++ b/districtgenerator/classes/certificate_generator.py @@ -3371,8 +3371,7 @@ def __init__(self, data, kpis, result_path) -> None: os.makedirs(self.result_path, exist_ok=True) self.outputpath = os.path.join(result_path, f"Quartiersenergieausweis_{self.scenario_name}.pdf") else: - src_path = os.path.dirname(os.path.dirname(os.path.abspath(__file__))) - self.outputpath = os.path.join(src_path, "results", f"Quartiersenergieausweis_{self.scenario_name}.pdf") + self.outputpath = os.path.join(os.getcwd(), "results", f"Quartiersenergieausweis_{self.scenario_name}.pdf") margins = self.style.get_page_margins() self.page_margins = { diff --git a/districtgenerator/classes/datahandler.py b/districtgenerator/classes/datahandler.py index edeea03e..c8c0ffbd 100644 --- a/districtgenerator/classes/datahandler.py +++ b/districtgenerator/classes/datahandler.py @@ -124,7 +124,7 @@ def __init__(self, if resultPath is not None: self.resultPath = resultPath else: - self.resultPath = os.path.join(self.srcPath, 'results') + self.resultPath = os.path.join(os.getcwd(), 'results') self.load_all_data(env_path=env_path, scenario_name=scenario_name) diff --git a/districtgenerator/classes/plots.py b/districtgenerator/classes/plots.py index 1be98288..288ecb88 100644 --- a/districtgenerator/classes/plots.py +++ b/districtgenerator/classes/plots.py @@ -22,11 +22,10 @@ def __init__(self, resultPath = None): None. """ - self.srcPath = os.path.dirname(os.path.dirname(os.path.abspath(__file__))) if resultPath is not None: self.resultPath = resultPath else: - self.resultPath = os.path.join(self.srcPath, 'results') + self.resultPath = os.path.join(os.getcwd(), 'results') def preparePlots(self, data): """ diff --git a/districtgenerator/data_handling/config.py b/districtgenerator/data_handling/config.py index 25165268..bfbef31a 100644 --- a/districtgenerator/data_handling/config.py +++ b/districtgenerator/data_handling/config.py @@ -1443,32 +1443,20 @@ class GlobalConfig(BaseModel): calendar: 'CalendarConfig' scenario_name: ScenarioName report: 'ReportConfig' -class Settings(BaseSettings): - """ - Settings class to manage global configuration parameters. - This class is used to load configuration parameters from an environment file. - """ - env_file: str = '.env.CONFIG.EXAMPLE' - - class Config: - env_file = '.env.CONFIG.EXAMPLE' # Default .env file if no env_file is provided - env_file_encoding = 'utf-8' - extra = 'ignore' # Ignores all other variables in the .env.CONFIG file - - def load_global_config(env_file: Optional[str] = None) -> GlobalConfig: """ Load the global configuration from the specified environment file. - If no environment file is provided, it defaults to standard parameters defined in the config classes. - For error handling, it prints the used environment file path. + If no environment file is provided, class defaults are used without loading a file. Note: All parameters defined in '.env.CONFIG.' will override the default values in config.py Parameters ---------- env_file : Optional[str] - The path to the environment file. If None, it uses the default from Settings. - Place config in the data folder of the districtgenerator package to use ".env.NAME" or use - absolute paths "c:/path/to/.env.CONFIG.EXAMPLE" or "/path/to/.env.CONFIG.EXAMPLE". + Path to the environment file. Absolute paths are used as-is. Relative paths are + resolved against the current working directory first; if not found there, the + package's bundled data directory is tried as a fallback (so bundled example + configs like '.env.CONFIG.EXAMPLE' work without copying them). + If None, all configuration classes use their built-in default values. Returns ------- @@ -1477,23 +1465,42 @@ def load_global_config(env_file: Optional[str] = None) -> GlobalConfig: """ if env_file is None: - settings = Settings() # Load settings from the .env file - env_file = settings.env_file - - script_path = Path(__file__).resolve() - project_root = script_path.parent.parent - - env_file_path = str(project_root / "data" / env_file) - - if not os.path.exists(env_file_path): - raise FileNotFoundError( - f"Configuration file not found. \n" - f" - Looked for: {env_file_path}\n" - f" - Based on script location: {script_path}" + return GlobalConfig( + location=LocationConfig(), + time=TimeConfig(), + design_building=DesignBuildingConfig(), + eco=EcoConfig(), + physics=PhysicsConfig(), + pyomo=PyomoConfig(), + heatgrid=HeatGridConfig(), + ehdo=EHDOConfig(), + decentral=DecentralDeviceConfig(), + central=CentralDeviceConfig(), + calendar=CalendarConfig(), + scenario_name=ScenarioName(), + report=ReportConfig() ) + p = Path(env_file) + if p.is_absolute(): + env_file_path = p + else: + cwd_candidate = Path(os.getcwd()) / p + package_candidate = Path(__file__).resolve().parent.parent / "data" / p + if cwd_candidate.exists(): + env_file_path = cwd_candidate + elif package_candidate.exists(): + env_file_path = package_candidate + else: + raise FileNotFoundError( + f"Configuration file not found.\n" + f" - Tried (CWD): {cwd_candidate}\n" + f" - Tried (package): {package_candidate}" + ) + + env_file_path = str(env_file_path) os.environ["ENV_FILE"] = env_file_path - print(f'Using config: {os.environ["ENV_FILE"]}') + print(f'Using config: {env_file_path}') return GlobalConfig( location=LocationConfig(_env_file=env_file_path), diff --git a/setup.py b/setup.py index 527b36e0..59bbff99 100644 --- a/setup.py +++ b/setup.py @@ -15,6 +15,9 @@ license='MIT License', packages=setuptools.find_packages(), include_package_data=True, + package_data={ + 'districtgenerator': ['data/**/*', 'data/*'], + }, install_requires=requirements, classifiers=("Programming Language :: Python :: 3", ), ) \ No newline at end of file