daemon: updated config.py to use dataclasses for config classes, updated naming and referencing. updated configurable options to self validate default values align with the config type. updated the example emane model to better align with the current state of things

This commit is contained in:
Blake Harnden 2021-03-31 11:13:40 -07:00
parent bb3590fbde
commit 6086d1229b
14 changed files with 171 additions and 133 deletions

View file

@ -4,10 +4,12 @@ Common support for configurable CORE objects.
import logging
from collections import OrderedDict
from typing import TYPE_CHECKING, Any, Dict, List, Optional, Tuple, Type, Union
from dataclasses import dataclass, field
from typing import TYPE_CHECKING, Any, Dict, List, Optional, Set, Tuple, Type, Union
from core.emane.nodes import EmaneNet
from core.emulator.enumerations import ConfigDataTypes
from core.errors import CoreConfigError
from core.nodes.network import WlanNode
if TYPE_CHECKING:
@ -15,62 +17,56 @@ if TYPE_CHECKING:
WirelessModelType = Type[WirelessModel]
_BOOL_OPTIONS: Set[str] = {"0", "1"}
@dataclass
class ConfigGroup:
"""
Defines configuration group tabs used for display by ConfigurationOptions.
"""
def __init__(self, name: str, start: int, stop: int) -> None:
"""
Creates a ConfigGroup object.
:param name: configuration group display name
:param start: configurations start index for this group
:param stop: configurations stop index for this group
"""
self.name: str = name
self.start: int = start
self.stop: int = stop
name: str
start: int
stop: int
@dataclass
class Configuration:
"""
Represents a configuration options.
"""
def __init__(
self,
_id: str,
_type: ConfigDataTypes,
label: str = None,
default: str = "",
options: List[str] = None,
) -> None:
"""
Creates a Configuration object.
id: str
type: ConfigDataTypes
label: str = None
default: str = ""
options: List[str] = field(default_factory=list)
:param _id: unique name for configuration
:param _type: configuration data type
:param label: configuration label for display
:param default: default value for configuration
:param options: list options if this is a configuration with a combobox
"""
self.id: str = _id
self.type: ConfigDataTypes = _type
self.default: str = default
if not options:
options = []
self.options: List[str] = options
if not label:
label = _id
self.label: str = label
def __str__(self):
return (
f"{self.__class__.__name__}(id={self.id}, type={self.type}, "
f"default={self.default}, options={self.options})"
)
def __post_init__(self) -> None:
self.label = self.label if self.label else self.id
if self.type == ConfigDataTypes.BOOL:
if self.default and self.default not in _BOOL_OPTIONS:
raise CoreConfigError(
f"{self.id} bool value must be one of: {_BOOL_OPTIONS}: "
f"{self.default}"
)
elif self.type == ConfigDataTypes.FLOAT:
if self.default:
try:
float(self.default)
except ValueError:
raise CoreConfigError(
f"{self.id} is not a valid float: {self.default}"
)
elif self.type != ConfigDataTypes.STRING:
if self.default:
try:
int(self.default)
except ValueError:
raise CoreConfigError(
f"{self.id} is not a valid int: {self.default}"
)
class ConfigurableOptions: