]> git.openstreetmap.org Git - nominatim.git/blobdiff - src/nominatim_db/config.py
Merge pull request #3582 from lonvia/switch-to-flake
[nominatim.git] / src / nominatim_db / config.py
index c4264f0d68ef17c0a182a1063c0a970862cf5aec..ad54ab3d3f195e42bd09449eaa58bef64194d5d9 100644 (file)
@@ -7,7 +7,7 @@
 """
 Nominatim configuration accessor.
 """
 """
 Nominatim configuration accessor.
 """
-from typing import Dict, Any, List, Mapping, Optional
+from typing import Union, Dict, Any, List, Mapping, Optional
 import importlib.util
 import logging
 import os
 import importlib.util
 import logging
 import os
@@ -18,17 +18,15 @@ import yaml
 
 from dotenv import dotenv_values
 
 
 from dotenv import dotenv_values
 
-try:
-    from psycopg2.extensions import parse_dsn
-except ModuleNotFoundError:
-    from psycopg.conninfo import conninfo_to_dict as parse_dsn # type: ignore[assignment]
+from psycopg.conninfo import conninfo_to_dict
 
 from .typing import StrPath
 from .errors import UsageError
 from . import paths
 
 LOG = logging.getLogger()
 
 from .typing import StrPath
 from .errors import UsageError
 from . import paths
 
 LOG = logging.getLogger()
-CONFIG_CACHE : Dict[str, Any] = {}
+CONFIG_CACHE: Dict[str, Any] = {}
+
 
 def flatten_config_list(content: Any, section: str = '') -> List[Any]:
     """ Flatten YAML configuration lists that contain include sections
 
 def flatten_config_list(content: Any, section: str = '') -> List[Any]:
     """ Flatten YAML configuration lists that contain include sections
@@ -62,34 +60,32 @@ class Configuration:
         other than string.
     """
 
         other than string.
     """
 
-    def __init__(self, project_dir: Optional[Path],
+    def __init__(self, project_dir: Optional[Union[Path, str]],
                  environ: Optional[Mapping[str, str]] = None) -> None:
                  environ: Optional[Mapping[str, str]] = None) -> None:
-        self.environ = environ or os.environ
-        self.project_dir = project_dir
+        self.environ = os.environ if environ is None else environ
         self.config_dir = paths.CONFIG_DIR
         self._config = dotenv_values(str(self.config_dir / 'env.defaults'))
         self.config_dir = paths.CONFIG_DIR
         self._config = dotenv_values(str(self.config_dir / 'env.defaults'))
-        if self.project_dir is not None and (self.project_dir / '.env').is_file():
-            self.project_dir = self.project_dir.resolve()
-            self._config.update(dotenv_values(str(self.project_dir / '.env')))
+        if project_dir is not None:
+            self.project_dir: Optional[Path] = Path(project_dir).resolve()
+            if (self.project_dir / '.env').is_file():
+                self._config.update(dotenv_values(str(self.project_dir / '.env')))
+        else:
+            self.project_dir = None
 
         class _LibDirs:
 
         class _LibDirs:
-            module: Path
             osm2pgsql: Path
             osm2pgsql: Path
-            php = paths.PHPLIB_DIR
             sql = paths.SQLLIB_DIR
             data = paths.DATA_DIR
 
         self.lib_dir = _LibDirs()
         self._private_plugins: Dict[str, object] = {}
 
             sql = paths.SQLLIB_DIR
             data = paths.DATA_DIR
 
         self.lib_dir = _LibDirs()
         self._private_plugins: Dict[str, object] = {}
 
-
     def set_libdirs(self, **kwargs: StrPath) -> None:
         """ Set paths to library functions and data.
         """
         for key, value in kwargs.items():
             setattr(self.lib_dir, key, None if value is None else Path(value))
 
     def set_libdirs(self, **kwargs: StrPath) -> None:
         """ Set paths to library functions and data.
         """
         for key, value in kwargs.items():
             setattr(self.lib_dir, key, None if value is None else Path(value))
 
-
     def __getattr__(self, name: str) -> str:
         name = 'NOMINATIM_' + name
 
     def __getattr__(self, name: str) -> str:
         name = 'NOMINATIM_' + name
 
@@ -98,7 +94,6 @@ class Configuration:
 
         return self._config[name] or ''
 
 
         return self._config[name] or ''
 
-
     def get_bool(self, name: str) -> bool:
         """ Return the given configuration parameter as a boolean.
 
     def get_bool(self, name: str) -> bool:
         """ Return the given configuration parameter as a boolean.
 
@@ -111,7 +106,6 @@ class Configuration:
         """
         return getattr(self, name).lower() in ('1', 'yes', 'true')
 
         """
         return getattr(self, name).lower() in ('1', 'yes', 'true')
 
-
     def get_int(self, name: str) -> int:
         """ Return the given configuration parameter as an int.
 
     def get_int(self, name: str) -> int:
         """ Return the given configuration parameter as an int.
 
@@ -131,11 +125,10 @@ class Configuration:
             LOG.fatal("Invalid setting NOMINATIM_%s. Needs to be a number.", name)
             raise UsageError("Configuration error.") from exp
 
             LOG.fatal("Invalid setting NOMINATIM_%s. Needs to be a number.", name)
             raise UsageError("Configuration error.") from exp
 
-
     def get_str_list(self, name: str) -> Optional[List[str]]:
         """ Return the given configuration parameter as a list of strings.
             The values are assumed to be given as a comma-sparated list and
     def get_str_list(self, name: str) -> Optional[List[str]]:
         """ Return the given configuration parameter as a list of strings.
             The values are assumed to be given as a comma-sparated list and
-            will be stripped before returning them. 
+            will be stripped before returning them.
 
             Parameters:
               name: Name of the configuration parameter with the NOMINATIM_
 
             Parameters:
               name: Name of the configuration parameter with the NOMINATIM_
@@ -151,7 +144,6 @@ class Configuration:
 
         return [v.strip() for v in raw.split(',')] if raw else None
 
 
         return [v.strip() for v in raw.split(',')] if raw else None
 
-
     def get_path(self, name: str) -> Optional[Path]:
         """ Return the given configuration parameter as a Path.
 
     def get_path(self, name: str) -> Optional[Path]:
         """ Return the given configuration parameter as a Path.
 
@@ -177,7 +169,6 @@ class Configuration:
 
         return cfgpath.resolve()
 
 
         return cfgpath.resolve()
 
-
     def get_libpq_dsn(self) -> str:
         """ Get configured database DSN converted into the key/value format
             understood by libpq and psycopg.
     def get_libpq_dsn(self) -> str:
         """ Get configured database DSN converted into the key/value format
             understood by libpq and psycopg.
@@ -197,8 +188,7 @@ class Configuration:
 
         return dsn
 
 
         return dsn
 
-
-    def get_database_params(self) -> Mapping[str, str]:
+    def get_database_params(self) -> Mapping[str, Union[str, int, None]]:
         """ Get the configured parameters for the database connection
             as a mapping.
         """
         """ Get the configured parameters for the database connection
             as a mapping.
         """
@@ -207,8 +197,7 @@ class Configuration:
         if dsn.startswith('pgsql:'):
             return dict((p.split('=', 1) for p in dsn[6:].split(';')))
 
         if dsn.startswith('pgsql:'):
             return dict((p.split('=', 1) for p in dsn[6:].split(';')))
 
-        return parse_dsn(dsn)
-
+        return conninfo_to_dict(dsn)
 
     def get_import_style_file(self) -> Path:
         """ Return the import style file as a path object. Translates the
 
     def get_import_style_file(self) -> Path:
         """ Return the import style file as a path object. Translates the
@@ -222,7 +211,6 @@ class Configuration:
 
         return self.find_config_file('', 'IMPORT_STYLE')
 
 
         return self.find_config_file('', 'IMPORT_STYLE')
 
-
     def get_os_env(self) -> Dict[str, str]:
         """ Return a copy of the OS environment with the Nominatim configuration
             merged in.
     def get_os_env(self) -> Dict[str, str]:
         """ Return a copy of the OS environment with the Nominatim configuration
             merged in.
@@ -232,7 +220,6 @@ class Configuration:
 
         return env
 
 
         return env
 
-
     def load_sub_configuration(self, filename: StrPath,
                                config: Optional[str] = None) -> Any:
         """ Load additional configuration from a file. `filename` is the name
     def load_sub_configuration(self, filename: StrPath,
                                config: Optional[str] = None) -> Any:
         """ Load additional configuration from a file. `filename` is the name
@@ -270,7 +257,6 @@ class Configuration:
         CONFIG_CACHE[str(configfile)] = result
         return result
 
         CONFIG_CACHE[str(configfile)] = result
         return result
 
-
     def load_plugin_module(self, module_name: str, internal_path: str) -> Any:
         """ Load a Python module as a plugin.
 
     def load_plugin_module(self, module_name: str, internal_path: str) -> Any:
         """ Load a Python module as a plugin.
 
@@ -313,7 +299,6 @@ class Configuration:
 
         return sys.modules.get(module_name) or importlib.import_module(module_name)
 
 
         return sys.modules.get(module_name) or importlib.import_module(module_name)
 
-
     def find_config_file(self, filename: StrPath,
                          config: Optional[str] = None) -> Path:
         """ Resolve the location of a configuration file given a filename and
     def find_config_file(self, filename: StrPath,
                          config: Optional[str] = None) -> Path:
         """ Resolve the location of a configuration file given a filename and
@@ -337,7 +322,6 @@ class Configuration:
 
                 filename = cfg_filename
 
 
                 filename = cfg_filename
 
-
         search_paths = [self.project_dir, self.config_dir]
         for path in search_paths:
             if path is not None and (path / filename).is_file():
         search_paths = [self.project_dir, self.config_dir]
         for path in search_paths:
             if path is not None and (path / filename).is_file():
@@ -347,7 +331,6 @@ class Configuration:
                   filename, search_paths)
         raise UsageError("Config file not found.")
 
                   filename, search_paths)
         raise UsageError("Config file not found.")
 
-
     def _load_from_yaml(self, cfgfile: Path) -> Any:
         """ Load a YAML configuration file. This installs a special handler that
             allows to include other YAML files using the '!include' operator.
     def _load_from_yaml(self, cfgfile: Path) -> Any:
         """ Load a YAML configuration file. This installs a special handler that
             allows to include other YAML files using the '!include' operator.
@@ -356,7 +339,6 @@ class Configuration:
                              Loader=yaml.SafeLoader)
         return yaml.safe_load(cfgfile.read_text(encoding='utf-8'))
 
                              Loader=yaml.SafeLoader)
         return yaml.safe_load(cfgfile.read_text(encoding='utf-8'))
 
-
     def _yaml_include_representer(self, loader: Any, node: yaml.Node) -> Any:
         """ Handler for the '!include' operator in YAML files.
 
     def _yaml_include_representer(self, loader: Any, node: yaml.Node) -> Any:
         """ Handler for the '!include' operator in YAML files.