classutils.py 1.6 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849
  1. #
  2. # Copyright OpenEmbedded Contributors
  3. #
  4. # SPDX-License-Identifier: GPL-2.0-only
  5. #
  6. class ClassRegistryMeta(type):
  7. """Give each ClassRegistry their own registry"""
  8. def __init__(cls, name, bases, attrs):
  9. cls.registry = {}
  10. type.__init__(cls, name, bases, attrs)
  11. class ClassRegistry(type, metaclass=ClassRegistryMeta):
  12. """Maintain a registry of classes, indexed by name.
  13. Note that this implementation requires that the names be unique, as it uses
  14. a dictionary to hold the classes by name.
  15. The name in the registry can be overridden via the 'name' attribute of the
  16. class, and the 'priority' attribute controls priority. The prioritized()
  17. method returns the registered classes in priority order.
  18. Subclasses of ClassRegistry may define an 'implemented' property to exert
  19. control over whether the class will be added to the registry (e.g. to keep
  20. abstract base classes out of the registry)."""
  21. priority = 0
  22. def __init__(cls, name, bases, attrs):
  23. super(ClassRegistry, cls).__init__(name, bases, attrs)
  24. try:
  25. if not cls.implemented:
  26. return
  27. except AttributeError:
  28. pass
  29. try:
  30. cls.name
  31. except AttributeError:
  32. cls.name = name
  33. cls.registry[cls.name] = cls
  34. @classmethod
  35. def prioritized(tcls):
  36. return sorted(list(tcls.registry.values()),
  37. key=lambda v: (v.priority, v.name), reverse=True)
  38. def unregister(cls):
  39. for key in cls.registry.keys():
  40. if cls.registry[key] is cls:
  41. del cls.registry[key]