From 62267d2d3ca6a7626479947c061dcb0d168c12e5 Mon Sep 17 00:00:00 2001 From: Sebastian Wagner Date: Fri, 29 Jan 2021 17:16:55 +0100 Subject: [PATCH] mgr/cephadm: Add pytest to verify delayed service deletion Signed-off-by: Sebastian Wagner --- src/pybind/mgr/cephadm/inventory.py | 19 ++++++++++++++++++- src/pybind/mgr/cephadm/tests/fixtures.py | 13 ++++++++++++- 2 files changed, 30 insertions(+), 2 deletions(-) diff --git a/src/pybind/mgr/cephadm/inventory.py b/src/pybind/mgr/cephadm/inventory.py index 0e43bc607d4..f54d3f2468b 100644 --- a/src/pybind/mgr/cephadm/inventory.py +++ b/src/pybind/mgr/cephadm/inventory.py @@ -2,7 +2,8 @@ import datetime from copy import copy import json import logging -from typing import TYPE_CHECKING, Dict, List, Iterator, Optional, Any, Tuple, Set, Mapping, cast +from typing import TYPE_CHECKING, Dict, List, Iterator, Optional, Any, Tuple, Set, Mapping, cast, \ + NamedTuple import orchestrator from ceph.deployment import inventory @@ -113,6 +114,12 @@ class Inventory: self.mgr.set_store('inventory', json.dumps(self._inventory)) +class SpecDescription(NamedTuple): + spec: ServiceSpec + created: datetime.datetime + deleted: Optional[datetime.datetime] + + class SpecStore(): def __init__(self, mgr): # type: (CephadmOrchestrator) -> None @@ -129,6 +136,16 @@ class SpecStore(): """ return self._specs + def __contains__(self, name: str) -> bool: + return name in self._specs + + def __getitem__(self, name: str) -> SpecDescription: + if name not in self._specs: + raise OrchestratorError(f'Service {name} not found.') + return SpecDescription(self._specs[name], + self.spec_created[name], + self.spec_deleted.get(name, None)) + @property def active_specs(self) -> Mapping[str, ServiceSpec]: return {k: v for k, v in self._specs.items() if k not in self.spec_deleted} diff --git a/src/pybind/mgr/cephadm/tests/fixtures.py b/src/pybind/mgr/cephadm/tests/fixtures.py index 8ebbb7cd0dd..a56383fd656 100644 --- a/src/pybind/mgr/cephadm/tests/fixtures.py +++ b/src/pybind/mgr/cephadm/tests/fixtures.py @@ -101,9 +101,20 @@ def with_host(m: CephadmOrchestrator, name, refresh_hosts=True): wait(m, m.remove_host(name)) -def assert_rm_service(cephadm, srv_name): +def assert_rm_service(cephadm: CephadmOrchestrator, srv_name): + mon_or_mgr = cephadm.spec_store[srv_name].spec.service_type in ('mon', 'mgr') + if mon_or_mgr: + assert 'Unable' in wait(cephadm, cephadm.remove_service(srv_name)) + return assert wait(cephadm, cephadm.remove_service(srv_name)) == f'Removed service {srv_name}' + assert cephadm.spec_store[srv_name].deleted is not None + CephadmServe(cephadm)._check_daemons() CephadmServe(cephadm)._apply_all_services() + assert cephadm.spec_store[srv_name].deleted + unmanaged = cephadm.spec_store[srv_name].spec.unmanaged + CephadmServe(cephadm)._purge_deleted_services() + if not unmanaged: # cause then we're not deleting daemons + assert srv_name not in cephadm.spec_store, f'{cephadm.spec_store[srv_name]!r}' @contextmanager -- 2.39.5