Source code for icalendar.cal.component_factory

"""A factory to create components."""

from __future__ import annotations

import re
from typing import TYPE_CHECKING

from icalendar.caselessdict import CaselessDict

if TYPE_CHECKING:
    from icalendar import Component


[docs] class ComponentFactory(CaselessDict): """Registered components from :rfc:`7953` and :rfc:`5545`. To get a component, use this class as shown below. .. code-block:: pycon >>> from icalendar import ComponentFactory >>> factory = ComponentFactory() >>> event_class = factory.get_component_class('VEVENT') >>> event_class() VEVENT({}) If a component class is not yet supported, it can be either created using :meth:`get_component_class` or added manually as a subclass of :class:`~icalendar.Component`. """ def __init__(self, *args, **kwargs): """Set keys to upper for initial dict.""" super().__init__(*args, **kwargs) from icalendar.cal.alarm import Alarm from icalendar.cal.availability import Availability from icalendar.cal.available import Available from icalendar.cal.calendar import Calendar from icalendar.cal.event import Event from icalendar.cal.free_busy import FreeBusy from icalendar.cal.journal import Journal from icalendar.cal.timezone import Timezone, TimezoneDaylight, TimezoneStandard from icalendar.cal.todo import Todo self.add_component_class(Calendar) self.add_component_class(Event) self.add_component_class(Todo) self.add_component_class(Journal) self.add_component_class(FreeBusy) self.add_component_class(Timezone) self.add_component_class(TimezoneStandard) self.add_component_class(TimezoneDaylight) self.add_component_class(Alarm) self.add_component_class(Available) self.add_component_class(Availability)
[docs] def add_component_class(self, cls: type[Component]) -> None: """Add a component class to the factory. Args: cls: The component class to add. """ self[cls.name] = cls
[docs] def get_component_class(self, name: str) -> type[Component]: """Get the component class from the factory. This also creates and adds the component class if it does not exist. Args: name: The name of the component, for example, ``"VCALENDAR"``. Returns: The registered component class. """ component_class = self.get(name) if component_class is None: from icalendar.cal.component import Component component_class = type( re.sub(r"[^\w]+", "", name), (Component,), {"name": name.upper()} ) self.add_component_class(component_class) return component_class
__all__ = ["ComponentFactory"]