when.py
1 from abc import ABC, abstractmethod 2 from datetime import datetime 3 from typing import Annotated 4 5 from pydantic import BaseModel, BeforeValidator 6 7 from sirocco.parsing._utils import convert_to_date, convert_to_date_or_none 8 9 10 class When(ABC): 11 @abstractmethod 12 def is_active(self, date: datetime | None) -> bool: 13 raise NotImplementedError 14 15 16 class AnyWhen(When): 17 def is_active(self, date: datetime | None) -> bool: # noqa: ARG002 # dummy argument needed 18 return True 19 20 21 class AtDate(When, BaseModel): 22 at: Annotated[datetime, BeforeValidator(convert_to_date)] 23 24 def is_active(self, date: datetime | None) -> bool: 25 if date is None: 26 msg = "Cannot use a when.at specification in a one-off cycle" 27 raise ValueError(msg) 28 return date == self.at 29 30 31 class BeforeAfterDate(When, BaseModel): 32 before: Annotated[datetime | None, BeforeValidator(convert_to_date_or_none)] = None 33 after: Annotated[datetime | None, BeforeValidator(convert_to_date_or_none)] = None 34 35 def is_active(self, date: datetime | None) -> bool: 36 if date is None: 37 msg = "Cannot use a when.before or when.after specification in a one-off cycle" 38 raise ValueError(msg) 39 return (self.before is None or date < self.before) and (self.after is None or date > self.after)