import logging
-try:
- from typing import List, Optional
-except ImportError:
- pass
+from typing import List, Optional, Dict, Callable
from ..inventory import Device
-from ..drive_group import DriveGroupSpec, DeviceSelection
+from ..drive_group import DriveGroupSpec, DeviceSelection, DriveGroupValidationError
from .filter import FilterGenerator
+from .matchers import _MatchInvalid
logger = logging.getLogger(__name__)
+def to_dg_exception(f: Callable) -> Callable[['DriveSelection', str,
+ Optional['DeviceSelection']],
+ List['Device']]:
+ def wrapper(self: 'DriveSelection', name: str, ds: Optional['DeviceSelection']) -> List[Device]:
+ try:
+ return f(self, ds)
+ except _MatchInvalid as e:
+ raise DriveGroupValidationError(f'{self.spec.service_id}.{name}', e.args[0])
+ return wrapper
+
+
class DriveSelection(object):
def __init__(self,
spec, # type: DriveGroupSpec
self.spec = spec
self.existing_daemons = existing_daemons or 0
- self._data = self.assign_devices(self.spec.data_devices)
- self._wal = self.assign_devices(self.spec.wal_devices)
- self._db = self.assign_devices(self.spec.db_devices)
- self._journal = self.assign_devices(self.spec.journal_devices)
+ self._data = self.assign_devices('data_devices', self.spec.data_devices)
+ self._wal = self.assign_devices('wal_devices', self.spec.wal_devices)
+ self._db = self.assign_devices('db_devices', self.spec.db_devices)
+ self._journal = self.assign_devices('journal_devices', self.spec.journal_devices)
def data_devices(self):
# type: () -> List[Device]
raise Exception(
"Disk {} doesn't have a 'path' identifier".format(disk))
+ @to_dg_exception
def assign_devices(self, device_filter):
# type: (Optional[DeviceSelection]) -> List[Device]
""" Assign drives based on used filters
self.disks.remove(taken_device)
return sorted([x for x in devices], key=lambda dev: dev.path)
+
+ def __repr__(self) -> str:
+ selection: Dict[str, List[str]] = {
+ 'data devices': [d.path for d in self._data],
+ 'wal_devices': [d.path for d in self._wal],
+ 'db devices': [d.path for d in self._db],
+ 'journal devices': [d.path for d in self._journal]
+ }
+ return "DeviceSelection({})".format(
+ ', '.join('{}={}'.format(key, selection[key]) for key in selection.keys())
+ )