mirror of
https://github.com/dw-0/kiauh.git
synced 2025-12-13 10:34:28 +05:00
refactor: improve typesafety KiauhSettings
Signed-off-by: Dominik Willner <th33xitus@gmail.com>
This commit is contained in:
@@ -10,7 +10,7 @@ from __future__ import annotations
|
|||||||
|
|
||||||
import shutil
|
import shutil
|
||||||
from dataclasses import dataclass, field
|
from dataclasses import dataclass, field
|
||||||
from typing import Any, List, Literal
|
from typing import Any, Callable, List, TypeVar
|
||||||
|
|
||||||
from components.klipper import KLIPPER_REPO_URL
|
from components.klipper import KLIPPER_REPO_URL
|
||||||
from components.moonraker import MOONRAKER_REPO_URL
|
from components.moonraker import MOONRAKER_REPO_URL
|
||||||
@@ -27,6 +27,8 @@ from kiauh import PROJECT_ROOT
|
|||||||
DEFAULT_CFG = PROJECT_ROOT.joinpath("default.kiauh.cfg")
|
DEFAULT_CFG = PROJECT_ROOT.joinpath("default.kiauh.cfg")
|
||||||
CUSTOM_CFG = PROJECT_ROOT.joinpath("kiauh.cfg")
|
CUSTOM_CFG = PROJECT_ROOT.joinpath("kiauh.cfg")
|
||||||
|
|
||||||
|
T = TypeVar("T")
|
||||||
|
|
||||||
|
|
||||||
class InvalidValueError(Exception):
|
class InvalidValueError(Exception):
|
||||||
"""Raised when a value is invalid for an option"""
|
"""Raised when a value is invalid for an option"""
|
||||||
@@ -152,8 +154,7 @@ class KiauhSettings:
|
|||||||
self.kiauh.backup_before_update = self.__read_from_cfg(
|
self.kiauh.backup_before_update = self.__read_from_cfg(
|
||||||
"kiauh",
|
"kiauh",
|
||||||
"backup_before_update",
|
"backup_before_update",
|
||||||
"bool",
|
self.config.getboolean,
|
||||||
False,
|
|
||||||
False,
|
False,
|
||||||
)
|
)
|
||||||
|
|
||||||
@@ -161,16 +162,15 @@ class KiauhSettings:
|
|||||||
self.klipper.use_python_binary = self.__read_from_cfg(
|
self.klipper.use_python_binary = self.__read_from_cfg(
|
||||||
"klipper",
|
"klipper",
|
||||||
"use_python_binary",
|
"use_python_binary",
|
||||||
"str",
|
self.config.getval,
|
||||||
None,
|
None,
|
||||||
True,
|
True,
|
||||||
)
|
)
|
||||||
kl_repos: List[str] = self.__read_from_cfg(
|
kl_repos: List[str] = self.__read_from_cfg(
|
||||||
"klipper",
|
"klipper",
|
||||||
"repositories",
|
"repositories",
|
||||||
"list",
|
self.config.getvals,
|
||||||
[KLIPPER_REPO_URL],
|
[KLIPPER_REPO_URL],
|
||||||
False,
|
|
||||||
)
|
)
|
||||||
self.klipper.repositories = self.__set_repo_state("klipper", kl_repos)
|
self.klipper.repositories = self.__set_repo_state("klipper", kl_repos)
|
||||||
|
|
||||||
@@ -178,23 +178,21 @@ class KiauhSettings:
|
|||||||
self.moonraker.use_python_binary = self.__read_from_cfg(
|
self.moonraker.use_python_binary = self.__read_from_cfg(
|
||||||
"moonraker",
|
"moonraker",
|
||||||
"use_python_binary",
|
"use_python_binary",
|
||||||
"str",
|
self.config.getval,
|
||||||
None,
|
None,
|
||||||
True,
|
True,
|
||||||
)
|
)
|
||||||
self.moonraker.optional_speedups = self.__read_from_cfg(
|
self.moonraker.optional_speedups = self.__read_from_cfg(
|
||||||
"moonraker",
|
"moonraker",
|
||||||
"optional_speedups",
|
"optional_speedups",
|
||||||
"bool",
|
self.config.getboolean,
|
||||||
True,
|
True,
|
||||||
False,
|
|
||||||
)
|
)
|
||||||
mr_repos: List[str] = self.__read_from_cfg(
|
mr_repos: List[str] = self.__read_from_cfg(
|
||||||
"moonraker",
|
"moonraker",
|
||||||
"repositories",
|
"repositories",
|
||||||
"list",
|
self.config.getvals,
|
||||||
[MOONRAKER_REPO_URL],
|
[MOONRAKER_REPO_URL],
|
||||||
False,
|
|
||||||
)
|
)
|
||||||
self.moonraker.repositories = self.__set_repo_state("moonraker", mr_repos)
|
self.moonraker.repositories = self.__set_repo_state("moonraker", mr_repos)
|
||||||
|
|
||||||
@@ -202,15 +200,13 @@ class KiauhSettings:
|
|||||||
self.mainsail.port = self.__read_from_cfg(
|
self.mainsail.port = self.__read_from_cfg(
|
||||||
"mainsail",
|
"mainsail",
|
||||||
"port",
|
"port",
|
||||||
"int",
|
self.config.getint,
|
||||||
80,
|
80,
|
||||||
False,
|
|
||||||
)
|
)
|
||||||
self.mainsail.unstable_releases = self.__read_from_cfg(
|
self.mainsail.unstable_releases = self.__read_from_cfg(
|
||||||
"mainsail",
|
"mainsail",
|
||||||
"unstable_releases",
|
"unstable_releases",
|
||||||
"bool",
|
self.config.getboolean,
|
||||||
False,
|
|
||||||
False,
|
False,
|
||||||
)
|
)
|
||||||
|
|
||||||
@@ -218,49 +214,52 @@ class KiauhSettings:
|
|||||||
self.fluidd.port = self.__read_from_cfg(
|
self.fluidd.port = self.__read_from_cfg(
|
||||||
"fluidd",
|
"fluidd",
|
||||||
"port",
|
"port",
|
||||||
"int",
|
self.config.getint,
|
||||||
80,
|
80,
|
||||||
False,
|
|
||||||
)
|
)
|
||||||
self.fluidd.unstable_releases = self.__read_from_cfg(
|
self.fluidd.unstable_releases = self.__read_from_cfg(
|
||||||
"fluidd",
|
"fluidd",
|
||||||
"unstable_releases",
|
"unstable_releases",
|
||||||
"bool",
|
self.config.getboolean,
|
||||||
False,
|
|
||||||
False,
|
False,
|
||||||
)
|
)
|
||||||
|
|
||||||
|
def __check_option_exists(
|
||||||
|
self, section: str, option: str, fallback: Any, silent: bool = False
|
||||||
|
) -> bool:
|
||||||
|
has_section = self.config.has_section(section)
|
||||||
|
has_option = self.config.has_option(section, option)
|
||||||
|
|
||||||
|
if not (has_section and has_option):
|
||||||
|
if not silent:
|
||||||
|
Logger.print_warn(
|
||||||
|
f"Option '{option}' in section '{section}' not defined. Falling back to '{fallback}'."
|
||||||
|
)
|
||||||
|
return False
|
||||||
|
return True
|
||||||
|
|
||||||
|
def __read_bool_from_cfg(
|
||||||
|
self,
|
||||||
|
section: str,
|
||||||
|
option: str,
|
||||||
|
fallback: bool | None = None,
|
||||||
|
silent: bool = False,
|
||||||
|
) -> bool | None:
|
||||||
|
if not self.__check_option_exists(section, option, fallback, silent):
|
||||||
|
return fallback
|
||||||
|
return self.config.getboolean(section, option, fallback)
|
||||||
|
|
||||||
def __read_from_cfg(
|
def __read_from_cfg(
|
||||||
self,
|
self,
|
||||||
section: str,
|
section: str,
|
||||||
option: str,
|
option: str,
|
||||||
value_type: Literal["str", "int", "bool", "list"] = "str",
|
getter: Callable[[str, str, T | None], T],
|
||||||
fallback: str | int | bool | List[str] | None = None,
|
fallback: T = None,
|
||||||
silent_fallback: bool = False,
|
silent: bool = False,
|
||||||
) -> str | int | bool | List[str] | None:
|
) -> T:
|
||||||
has_section = self.config.has_section(section)
|
if not self.__check_option_exists(section, option, fallback, silent):
|
||||||
has_option = self.config.has_option(section, option)
|
|
||||||
|
|
||||||
if not (has_section and has_option):
|
|
||||||
if not silent_fallback:
|
|
||||||
Logger.print_warn(
|
|
||||||
f"Option '{option}' in section '{section}' not defined. Falling back to '{fallback}'."
|
|
||||||
)
|
|
||||||
return fallback
|
|
||||||
|
|
||||||
try:
|
|
||||||
return {
|
|
||||||
"int": self.config.getint,
|
|
||||||
"bool": self.config.getboolean,
|
|
||||||
"list": self.config.getval,
|
|
||||||
"str": self.config.getval,
|
|
||||||
}[value_type](section, option)
|
|
||||||
except (ValueError, TypeError) as e:
|
|
||||||
if not silent_fallback:
|
|
||||||
Logger.print_warn(
|
|
||||||
f"Failed to parse value of option '{option}' in section '{section}' as {value_type}. Falling back to '{fallback}'. Error: {e}"
|
|
||||||
)
|
|
||||||
return fallback
|
return fallback
|
||||||
|
return getter(section, option, fallback)
|
||||||
|
|
||||||
def __set_repo_state(self, section: str, repos: List[str]) -> List[Repository]:
|
def __set_repo_state(self, section: str, repos: List[str]) -> List[Repository]:
|
||||||
_repos: List[Repository] = []
|
_repos: List[Repository] = []
|
||||||
|
|||||||
Reference in New Issue
Block a user