finished the core mechanic behind the config file
This commit is contained in:
parent
8143bb6608
commit
43de7f48c6
@ -4,4 +4,3 @@ from .audio import AUDIO_SECTION
|
||||
from .config import read, write
|
||||
|
||||
read()
|
||||
write()
|
||||
|
@ -122,6 +122,7 @@ There are multiple fields, you can use for the path and file name:
|
||||
self.DEFAULT_LABEL,
|
||||
self.DEFAULT_SONG
|
||||
]
|
||||
super().__init__()
|
||||
|
||||
|
||||
AUDIO_SECTION = AudioSection()
|
||||
|
@ -1,5 +1,6 @@
|
||||
import logging
|
||||
from dataclasses import dataclass
|
||||
from typing import Optional, List, Union
|
||||
from typing import Optional, List, Union, Dict
|
||||
|
||||
COMMENT_PREFIX = "#"
|
||||
|
||||
@ -27,6 +28,17 @@ class Attribute:
|
||||
description: Optional[str]
|
||||
value: Union[str, List[str]]
|
||||
|
||||
rule: str = "The setting {name} can't be {value}."
|
||||
|
||||
def set_value(self, value: str):
|
||||
_value = self.value
|
||||
|
||||
self.value = value
|
||||
try:
|
||||
_ = self.object_from_value
|
||||
except ValueError:
|
||||
raise ValueError(self.rule.format(name=self.name, value=self.value))
|
||||
|
||||
@property
|
||||
def description_as_comment(self):
|
||||
return comment_string(self.description)
|
||||
@ -50,6 +62,8 @@ class StringAttribute(SingleAttribute):
|
||||
|
||||
|
||||
class IntAttribute(SingleAttribute):
|
||||
rule = "The setting {name} has to be an integer, not {value}"
|
||||
|
||||
@property
|
||||
def object_from_value(self) -> int:
|
||||
if not self.value.isdigit():
|
||||
@ -59,6 +73,8 @@ class IntAttribute(SingleAttribute):
|
||||
|
||||
|
||||
class FloatAttribute(SingleAttribute):
|
||||
rule = "The setting {name} has to be a number, not {value}"
|
||||
|
||||
@property
|
||||
def object_from_value(self) -> float:
|
||||
if not self.value.isnumeric():
|
||||
@ -97,5 +113,27 @@ class Section:
|
||||
Description
|
||||
]]
|
||||
|
||||
def __init__(self):
|
||||
self.name_attribute_map: Dict[str, Attribute] = dict()
|
||||
self.index_values()
|
||||
|
||||
def __str__(self):
|
||||
return "\n".join(attribute.__str__() for attribute in self.attribute_list)
|
||||
|
||||
def index_values(self):
|
||||
for element in self.attribute_list:
|
||||
if not isinstance(element, Attribute):
|
||||
continue
|
||||
|
||||
if element.name in self.name_attribute_map:
|
||||
raise ValueError(f"Two different Attributes have the same name: "
|
||||
f"{self.name_attribute_map[element.name]} {element}")
|
||||
|
||||
self.name_attribute_map[element.name] = element
|
||||
|
||||
def __setitem__(self, key, value):
|
||||
if key not in self.name_attribute_map:
|
||||
raise KeyError(f"There is no such setting with the name: {key}")
|
||||
|
||||
attribute = self.name_attribute_map[key]
|
||||
attribute.set_value(value)
|
||||
|
@ -1,9 +1,9 @@
|
||||
from typing import Union, Tuple
|
||||
from typing import Union, Tuple, Dict
|
||||
import logging
|
||||
import os
|
||||
|
||||
from ..path_manager import LOCATIONS
|
||||
from .base_classes import Description, Attribute, Section, EmptyLine
|
||||
from .base_classes import Description, Attribute, Section, EmptyLine, COMMENT_PREFIX
|
||||
from .audio import AUDIO_SECTION
|
||||
from .logging import LOGGING_SECTION
|
||||
|
||||
@ -26,10 +26,52 @@ class Config:
|
||||
EmptyLine()
|
||||
)
|
||||
|
||||
self._name_section_map: Dict[str, Section] = dict()
|
||||
|
||||
for element in self.config_elements:
|
||||
if not isinstance(element, Section):
|
||||
continue
|
||||
|
||||
for name in element.name_attribute_map:
|
||||
if name in self._name_section_map:
|
||||
raise ValueError(f"Two sections have the same name: "
|
||||
f"{name}: "
|
||||
f"{element.__class__.__name__} {self._name_section_map[name].__class__.__name__}")
|
||||
|
||||
self._name_section_map[name] = element
|
||||
|
||||
def set_name_to_value(self, name: str, value: str):
|
||||
if name not in self._name_section_map:
|
||||
raise KeyError(f"There is no such setting, as: {name}")
|
||||
|
||||
self._name_section_map[name][name] = value
|
||||
|
||||
@property
|
||||
def config_string(self) -> str:
|
||||
return "\n\n".join(str(element) for element in self.config_elements)
|
||||
|
||||
def _parse_conf_line(self, line: str, index: int):
|
||||
line = line.strip()
|
||||
if line.startswith(COMMENT_PREFIX):
|
||||
return
|
||||
|
||||
if line == "":
|
||||
return
|
||||
|
||||
if "=" not in line:
|
||||
raise ValueError(f"Couldn't find the '=' in line {index}.")
|
||||
|
||||
line_segments = line.split("=")
|
||||
name = line_segments[0]
|
||||
value = "=".join(line_segments[1:])
|
||||
|
||||
self.set_name_to_value(name, value)
|
||||
|
||||
def read_from_config_file(self, path: os.PathLike):
|
||||
with open(path, "r") as conf_file:
|
||||
for i, line in enumerate(conf_file):
|
||||
self._parse_conf_line(line, i+1)
|
||||
|
||||
def write_to_config_file(self, path: os.PathLike):
|
||||
with open(path, "w") as conf_file:
|
||||
conf_file.write(self.config_string)
|
||||
@ -39,7 +81,9 @@ config = Config()
|
||||
|
||||
|
||||
def read():
|
||||
pass
|
||||
if not LOCATIONS.CONFIG_FILE.is_file():
|
||||
write()
|
||||
config.read_from_config_file(LOCATIONS.CONFIG_FILE)
|
||||
|
||||
|
||||
def write():
|
||||
|
@ -118,5 +118,7 @@ class LoggingSection(Section):
|
||||
self.GENIUS_LOGGER
|
||||
]
|
||||
|
||||
super().__init__()
|
||||
|
||||
|
||||
LOGGING_SECTION = LoggingSection()
|
||||
|
Loading…
Reference in New Issue
Block a user