from pathlib import Path import yaml as yams from configparser import ConfigParser as cfg from custtypes import ExecutedPath from re import compile as rgx, IGNORECASE from whereami import PROJ_ROOT from typing import Literal class Parser: def __init__(self): self.__is_yaml = rgx(r".*\.ya?ml$", flags=IGNORECASE).match self.__is_ini = rgx(r".*\.ini$", flags=IGNORECASE).match self.__is_config = rgx(r".*\.cfg$", flags=IGNORECASE).match self.__is_json = rgx(r".*\.[jb]son$", flags=IGNORECASE).match self.__data = None self.__content: str | None = None self.__is_path: bool = False # @TODO use Enum child class for below type hint instead self.__method: Literal["yaml", "config", "generic"] = "generic" self.__file: ExecutedPath | None = None def load(self, filepath: ExecutedPath | str, method: Literal["yaml", "config", "generic"] = "generic", **kwargs): if isinstance(filepath, ExecutedPath): self.__is_path = True self.__file = filepath filepath = str(filepath) else: if isinstance(filepath, str) and Path(filepath).exists(): self.__file = Path(filepath) self.__is_path = True else: self.__is_path = False if isinstance(filepath, str): self.__content = filepath if self.__is_yaml(filepath) or method == "yaml": self.__method = "yaml" if self.__is_path: filepath = open(str(filepath), "r+") if len(kwargs) > 0: self.__data = yams.load_all(filepath, Loader=yams.Loader, **kwargs) else: self.__data = yams.load_all(filepath, Loader=yams.Loader) filepath.close() elif self.__is_config(filepath) or method == "config": self.__method = "config" self.__data = cfg() if self.__is_path: read = self.__data.read else: read = self.__data.read_string if len(kwargs) > 0: self.__data.read(filepath, **kwargs) else: self.__data.read(filepath) else: raise TypeError return self.__data def dump(self, obj = None, method: Literal["yaml", "config", "generic"] | None = "generic", **kwargs): if isinstance(obj, yams.YAMLObject) or self.__method == "yaml" or method == "yaml": if obj is None: obj = self.__data if len(kwargs) > 0: self.__content = "---\n" + yams.dump(obj, Dumper=yams.Dumper, **kwargs) else: self.__content = "---\n" + yams.dump(obj, Dumper=yams.Dumper) elif isinstance(obj, ConfigParser) or self.__method == "config" or method == "config": if obj is None: if self.__is_path: return self.__file.read_text() else: if self.__file is None: return self.__content else: return self.__file.read_text() raise NotImplementedError else: raise TypeError return self.__content