Split calendar event code into own file
This commit is contained in:
parent
b52a076c5b
commit
c24a83f161
|
@ -23,7 +23,7 @@ from dateutil.relativedelta import FR, relativedelta
|
||||||
|
|
||||||
from agenda import thespacedevs
|
from agenda import thespacedevs
|
||||||
|
|
||||||
from . import fx, gwr, markets, sun, waste_schedule
|
from . import calendar, fx, gwr, markets, sun, waste_schedule
|
||||||
from .types import Event
|
from .types import Event
|
||||||
|
|
||||||
warnings.simplefilter(action="ignore", category=FutureWarning)
|
warnings.simplefilter(action="ignore", category=FutureWarning)
|
||||||
|
@ -49,26 +49,8 @@ assert os.path.exists(config_filename)
|
||||||
config = configparser.ConfigParser()
|
config = configparser.ConfigParser()
|
||||||
config.read(config_filename)
|
config.read(config_filename)
|
||||||
|
|
||||||
access_key = config.get("exchangerate", "access_key")
|
|
||||||
data_dir = config.get("data", "dir")
|
data_dir = config.get("data", "dir")
|
||||||
|
|
||||||
colors = {
|
|
||||||
"primary-subtle": "#cfe2ff",
|
|
||||||
"secondary-subtle": "#e2e3e5",
|
|
||||||
"success-subtle": "#d1e7dd",
|
|
||||||
"info-subtle": "#cff4fc",
|
|
||||||
"warning-subtle": "#fff3cd",
|
|
||||||
"danger-subtle": "#f8d7da",
|
|
||||||
}
|
|
||||||
|
|
||||||
event_type_color_map = {
|
|
||||||
"bank_holiday": "success-subtle",
|
|
||||||
"conference": "primary-subtle",
|
|
||||||
"us_holiday": "secondary-subtle",
|
|
||||||
"birthday": "info-subtle",
|
|
||||||
"waste_schedule": "danger-subtle",
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
def next_uk_mothers_day(input_date: date) -> date:
|
def next_uk_mothers_day(input_date: date) -> date:
|
||||||
"""Calculate the date of the next UK Mother's Day from the current date."""
|
"""Calculate the date of the next UK Mother's Day from the current date."""
|
||||||
|
@ -288,7 +270,7 @@ def as_date(d: date | datetime) -> date:
|
||||||
return d.date() if isinstance(d, datetime) else d
|
return d.date() if isinstance(d, datetime) else d
|
||||||
|
|
||||||
|
|
||||||
def get_conferences(input_date: date, filepath: str) -> List[Event]:
|
def get_conferences(filepath: str) -> List[Event]:
|
||||||
"""Read conferences from a YAML file and return a list of Event objects."""
|
"""Read conferences from a YAML file and return a list of Event objects."""
|
||||||
with open(filepath, "r") as f:
|
with open(filepath, "r") as f:
|
||||||
data = yaml.safe_load(f)
|
data = yaml.safe_load(f)
|
||||||
|
@ -299,8 +281,6 @@ def get_conferences(input_date: date, filepath: str) -> List[Event]:
|
||||||
end_date = conf["end"]
|
end_date = conf["end"]
|
||||||
|
|
||||||
# Skip the conference if it is before the input date.
|
# Skip the conference if it is before the input date.
|
||||||
if as_date(end_date) < input_date:
|
|
||||||
continue
|
|
||||||
event = Event(
|
event = Event(
|
||||||
name="conference",
|
name="conference",
|
||||||
date=start_date,
|
date=start_date,
|
||||||
|
@ -448,60 +428,6 @@ def bristol_waste_collection_events(start_date: date) -> list[Event]:
|
||||||
return waste_schedule.get_bristol_gov_uk(start_date, data_dir, uprn)
|
return waste_schedule.get_bristol_gov_uk(start_date, data_dir, uprn)
|
||||||
|
|
||||||
|
|
||||||
def build_events_for_calendar(events: list[Event]) -> list[dict[str, typing.Any]]:
|
|
||||||
"""Build list of events for FullCalendar."""
|
|
||||||
items: list[dict[str, typing.Any]] = []
|
|
||||||
|
|
||||||
one_day = timedelta(days=1)
|
|
||||||
|
|
||||||
for e in events:
|
|
||||||
if e.name == "accommodation":
|
|
||||||
assert e.title and e.end_date
|
|
||||||
item = {
|
|
||||||
"allDay": True,
|
|
||||||
"title": e.display_title,
|
|
||||||
"start": e.as_date.isoformat(),
|
|
||||||
"end": (e.end_as_date + one_day).isoformat(),
|
|
||||||
"url": e.url,
|
|
||||||
}
|
|
||||||
items.append(item)
|
|
||||||
|
|
||||||
item = {
|
|
||||||
"allDay": False,
|
|
||||||
"title": "checkin: " + e.title,
|
|
||||||
"start": e.date.isoformat(),
|
|
||||||
"url": e.url,
|
|
||||||
}
|
|
||||||
items.append(item)
|
|
||||||
item = {
|
|
||||||
"allDay": False,
|
|
||||||
"title": "checkout: " + e.title,
|
|
||||||
"start": e.end_date.isoformat(),
|
|
||||||
"url": e.url,
|
|
||||||
}
|
|
||||||
items.append(item)
|
|
||||||
|
|
||||||
continue
|
|
||||||
|
|
||||||
if e.has_time:
|
|
||||||
end = e.end_date or e.date + timedelta(hours=1)
|
|
||||||
else:
|
|
||||||
end = (e.end_as_date if e.end_date else e.as_date) + one_day
|
|
||||||
item = {
|
|
||||||
"allDay": not e.has_time,
|
|
||||||
"title": e.display_title,
|
|
||||||
"start": e.date.isoformat(),
|
|
||||||
"end": end.isoformat(),
|
|
||||||
}
|
|
||||||
if e.name in event_type_color_map:
|
|
||||||
item["color"] = colors[event_type_color_map[e.name]]
|
|
||||||
item["textColor"] = "black"
|
|
||||||
if e.url:
|
|
||||||
item["url"] = e.url
|
|
||||||
items.append(item)
|
|
||||||
return items
|
|
||||||
|
|
||||||
|
|
||||||
def get_data(now: datetime) -> typing.Mapping[str, str | object]:
|
def get_data(now: datetime) -> typing.Mapping[str, str | object]:
|
||||||
"""Get data to display on agenda dashboard."""
|
"""Get data to display on agenda dashboard."""
|
||||||
rocket_dir = os.path.join(data_dir, "thespacedevs")
|
rocket_dir = os.path.join(data_dir, "thespacedevs")
|
||||||
|
@ -554,7 +480,7 @@ def get_data(now: datetime) -> typing.Mapping[str, str | object]:
|
||||||
events += get_birthdays(today, os.path.join(my_data, "entities.yaml"))
|
events += get_birthdays(today, os.path.join(my_data, "entities.yaml"))
|
||||||
events += get_accommodation(today, os.path.join(my_data, "accommodation.yaml"))
|
events += get_accommodation(today, os.path.join(my_data, "accommodation.yaml"))
|
||||||
events += get_all_travel_events(today)
|
events += get_all_travel_events(today)
|
||||||
events += get_conferences(today, os.path.join(my_data, "conferences.yaml"))
|
events += get_conferences(os.path.join(my_data, "conferences.yaml"))
|
||||||
events += waste_collection_events() + bristol_waste_collection_events(today)
|
events += waste_collection_events() + bristol_waste_collection_events(today)
|
||||||
|
|
||||||
next_up_series = Event(
|
next_up_series = Event(
|
||||||
|
@ -568,6 +494,6 @@ def get_data(now: datetime) -> typing.Mapping[str, str | object]:
|
||||||
|
|
||||||
reply["events"] = events
|
reply["events"] = events
|
||||||
|
|
||||||
reply["fullcalendar_events"] = build_events_for_calendar(events)
|
reply["fullcalendar_events"] = calendar.build_events(events)
|
||||||
|
|
||||||
return reply
|
return reply
|
||||||
|
|
77
agenda/calendar.py
Normal file
77
agenda/calendar.py
Normal file
|
@ -0,0 +1,77 @@
|
||||||
|
"""Calendar."""
|
||||||
|
|
||||||
|
import typing
|
||||||
|
from datetime import timedelta
|
||||||
|
|
||||||
|
from .types import Event
|
||||||
|
|
||||||
|
event_type_color_map = {
|
||||||
|
"bank_holiday": "success-subtle",
|
||||||
|
"conference": "primary-subtle",
|
||||||
|
"us_holiday": "secondary-subtle",
|
||||||
|
"birthday": "info-subtle",
|
||||||
|
"waste_schedule": "danger-subtle",
|
||||||
|
}
|
||||||
|
|
||||||
|
colors = {
|
||||||
|
"primary-subtle": "#cfe2ff",
|
||||||
|
"secondary-subtle": "#e2e3e5",
|
||||||
|
"success-subtle": "#d1e7dd",
|
||||||
|
"info-subtle": "#cff4fc",
|
||||||
|
"warning-subtle": "#fff3cd",
|
||||||
|
"danger-subtle": "#f8d7da",
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
def build_events(events: list[Event]) -> list[dict[str, typing.Any]]:
|
||||||
|
"""Build list of events for FullCalendar."""
|
||||||
|
items: list[dict[str, typing.Any]] = []
|
||||||
|
|
||||||
|
one_day = timedelta(days=1)
|
||||||
|
|
||||||
|
for e in events:
|
||||||
|
if e.name == "accommodation":
|
||||||
|
assert e.title and e.end_date
|
||||||
|
item = {
|
||||||
|
"allDay": True,
|
||||||
|
"title": e.display_title,
|
||||||
|
"start": e.as_date.isoformat(),
|
||||||
|
"end": (e.end_as_date + one_day).isoformat(),
|
||||||
|
"url": e.url,
|
||||||
|
}
|
||||||
|
items.append(item)
|
||||||
|
|
||||||
|
item = {
|
||||||
|
"allDay": False,
|
||||||
|
"title": "checkin: " + e.title,
|
||||||
|
"start": e.date.isoformat(),
|
||||||
|
"url": e.url,
|
||||||
|
}
|
||||||
|
items.append(item)
|
||||||
|
item = {
|
||||||
|
"allDay": False,
|
||||||
|
"title": "checkout: " + e.title,
|
||||||
|
"start": e.end_date.isoformat(),
|
||||||
|
"url": e.url,
|
||||||
|
}
|
||||||
|
items.append(item)
|
||||||
|
|
||||||
|
continue
|
||||||
|
|
||||||
|
if e.has_time:
|
||||||
|
end = e.end_date or e.date + timedelta(hours=1)
|
||||||
|
else:
|
||||||
|
end = (e.end_as_date if e.end_date else e.as_date) + one_day
|
||||||
|
item = {
|
||||||
|
"allDay": not e.has_time,
|
||||||
|
"title": e.display_title,
|
||||||
|
"start": e.date.isoformat(),
|
||||||
|
"end": end.isoformat(),
|
||||||
|
}
|
||||||
|
if e.name in event_type_color_map:
|
||||||
|
item["color"] = colors[event_type_color_map[e.name]]
|
||||||
|
item["textColor"] = "black"
|
||||||
|
if e.url:
|
||||||
|
item["url"] = e.url
|
||||||
|
items.append(item)
|
||||||
|
return items
|
Loading…
Reference in a new issue