MAP: Convert from DPO to input feature.
[vpp.git] / test / vpp_object.py
1 """ abstract vpp object and object registry """
2
3 from abc import ABCMeta, abstractmethod
4
5 from six import moves
6
7
8 class VppObject(object):
9     """ Abstract vpp object """
10     __metaclass__ = ABCMeta
11
12     @abstractmethod
13     def add_vpp_config(self):
14         """ Add the configuration for this object to vpp. """
15         pass
16
17     @abstractmethod
18     def query_vpp_config(self):
19         """Query the vpp configuration.
20
21         :return: True if the object is configured"""
22         pass
23
24     @abstractmethod
25     def remove_vpp_config(self):
26         """ Remove the configuration for this object from vpp. """
27         pass
28
29     @abstractmethod
30     def object_id(self):
31         """ Return a unique string representing this object. """
32         pass
33
34
35 class VppObjectRegistry(object):
36     """ Class which handles automatic configuration cleanup. """
37     _shared_state = {}
38
39     def __init__(self):
40         self.__dict__ = self._shared_state
41         if not hasattr(self, "_object_registry"):
42             self._object_registry = []
43         if not hasattr(self, "_object_dict"):
44             self._object_dict = dict()
45
46     def register(self, obj, logger):
47         """ Register an object in the registry. """
48         if obj.object_id() not in self._object_dict:
49             self._object_registry.append(obj)
50             self._object_dict[obj.object_id()] = obj
51             logger.debug("REG: registering %s" % obj)
52         else:
53             logger.debug("REG: duplicate add, ignoring (%s)" % obj)
54
55     def unregister_all(self, logger):
56         """ Remove all object registrations from registry. """
57         logger.debug("REG: removing all object registrations")
58         self._object_registry = []
59         self._object_dict = dict()
60
61     def remove_vpp_config(self, logger):
62         """
63         Remove configuration (if present) from vpp and then remove all objects
64         from the registry.
65         """
66         if not self._object_registry:
67             logger.info("REG: No objects registered for auto-cleanup.")
68             return
69         logger.info("REG: Removing VPP configuration for registered objects")
70         # remove the config in reverse order as there might be dependencies
71         failed = []
72         for obj in reversed(self._object_registry):
73             if obj.query_vpp_config():
74                 logger.info("REG: Removing configuration for %s" % obj)
75                 obj.remove_vpp_config()
76                 if obj.query_vpp_config():
77                     failed.append(obj)
78             else:
79                 logger.info(
80                     "REG: Skipping removal for %s, configuration not present" %
81                     obj)
82         self.unregister_all(logger)
83         if failed:
84             logger.error("REG: Couldn't remove configuration for object(s):")
85             for obj in failed:
86                 logger.error(moves.reprlib.repr(obj))
87             raise Exception("Couldn't remove configuration for object(s): %s" %
88                             (", ".join(str(x) for x in failed)))