create Event model

This commit is contained in:
2022-05-25 13:42:43 -05:00
parent 213bcf92d5
commit bcc5e04e5a
3 changed files with 142 additions and 35 deletions

99
app/models.py Normal file
View File

@@ -0,0 +1,99 @@
from datetime import datetime, date, timedelta, timezone
from caldav.objects import Event as CaldavEvent
import dataclasses
from icalendar import Event as IcEvent
from icalendar import Calendar as Icalendar
@dataclasses.dataclass
class Event():
summary: str
dtstart: datetime
dtend: datetime
is_all_day: bool
@classmethod
def fromCalDavEvents(cls, caldav_events: [CaldavEvent]) -> list['Event']:
events = []
for event in caldav_events:
date_value = event.vobject_instance.vevent.dtstart.value
if isinstance(date_value, datetime):
dt_start = date_value
is_all_day = False
elif isinstance(date_value, date):
d_start = date_value
dt_start = datetime(d_start.year, d_start.month, d_start.day, tzinfo=datetime.now(timezone.utc).astimezone().tzinfo)
is_all_day = True
else:
raise Exception
date_value = event.vobject_instance.vevent.dtend.value
if isinstance(date_value, datetime):
dt_end = date_value
elif isinstance(date_value, date):
d_end = date_value
dt_end = datetime(d_end.year, d_end.month, d_end.day,tzinfo=datetime.now(timezone.utc).astimezone().tzinfo)
date_value = dt_end
else:
raise Exception
events.append(Event(
summary=event.vobject_instance.vevent.summary.value,
dtstart=dt_start,
dtend=dt_end,
is_all_day = is_all_day
))
return events
@classmethod
def fromIcalendar(cls, icalendar: Icalendar) -> list['Event']:
events = []
for event in [e for e in icalendar.subcomponents if isinstance(e, IcEvent)]:
date_value = event['DTSTART'].dt
if isinstance(date_value, datetime):
dt_start = date_value
is_all_day = False
elif isinstance(date_value, date):
d_start = date_value
dt_start = datetime(d_start.year, d_start.month, d_start.day, tzinfo=datetime.now(timezone.utc).astimezone().tzinfo)
is_all_day = True
else:
raise Exception
date_value = event['DTEND'].dt if event.get('DTEND') else event['DTSTART'].dt
if isinstance(date_value, datetime):
dt_end = date_value
elif isinstance(date_value, date):
d_end = date_value
dt_end = datetime(d_end.year, d_end.month, d_end.day,tzinfo=datetime.now(timezone.utc).astimezone().tzinfo)
else:
raise Exception
events.append(Event(
summary=event['summary'],
dtstart=dt_start,
dtend=dt_end,
is_all_day = is_all_day
))
return events
@property
def range_str(self) -> str:
start_time_str = self.dtstart.strftime('%-I')
end_time_str = self.dtend.strftime('%-I')
if not(self.dtstart.hour and self.dtend.hour):
return ""
if self.dtstart.minute: start_time_str += self.dtstart.strftime(':%M')
if self.dtend.minute: end_time_str += self.dtend.strftime(':%M')
if not ((self.dtstart.hour < 12 and self.dtend.hour < 12) or (self.dtstart.hour > 12 and self.dtend.hour > 12)):
start_time_str += self.dtstart.strftime("%p")
end_time_str += self.dtend.strftime("%p")
return f"{start_time_str}-{end_time_str}"

View File

@@ -18,19 +18,19 @@
</div>
<div class="panel bottom week">
{% for day, event in days %}
{% for day, events in days %}
<div class="day">
<div id="dotw-1" class="day-title">
{{ day.strftime('%A') }}
</div>
{% if event %}
{% for event in events %}
<div class="event">
{{ event.summary.value }}<br>
{% if event.dtstart.value.strftime('%H') != "00" %}
{{ event.dtstart.value.strftime('%-I:%M %p') }}<br>{{ event.dtend.value.strftime('%-I:%M %p') }}
{{ event.summary }}<br>
{% if not event.is_all_day %}
<span class="daterange">{{ event.range_str }}</span>
{% endif %}
</div>
{% endif %}
{% endfor %}
</div>
{% endfor %}
</div>

View File

@@ -1,12 +1,13 @@
from app import app
from datetime import datetime, timedelta
from datetime import datetime, timedelta, timezone
import os
import caldav
import datetime
from icalendar import cal, Event
from flask import render_template
from .models import Event
import requests
url = os.getenv('caldav_url')
caldav_url = os.getenv('caldav_url')
username = os.getenv('username')
password = os.getenv('password')
cal_id = os.getenv('cal_id')
@@ -17,42 +18,49 @@ def daterange(start_date, end_date):
yield datetime.datetime.date(start_date + timedelta(n))
@app.route('/')
def hello_world():
date_obj = datetime.datetime.now()
start_of_week = date_obj - timedelta(days=date_obj.weekday()) # Monday
def dashboard():
today = datetime.datetime.now(tz=datetime.datetime.now(timezone.utc).astimezone().tzinfo)
# today = datetime.datetime(2022,5,30, tzinfo=datetime.datetime.now(timezone.utc).astimezone().tzinfo)
start_of_week = today - timedelta(days=today.weekday()) # Monday
end_of_week = start_of_week + timedelta(days=7) # Sunday
with caldav.DAVClient(url=url, username=username, password=password) as client:
events = []
for url in [
'https://www.calendarlabs.com/ical-calendar/ics/76/US_Holidays.ics',
]:
r = requests.get(url)
c = cal.Calendar.from_ical(r.content)
events += Event.fromIcalendar(c)
with caldav.DAVClient(url=caldav_url, username=username, password=password) as client:
my_principal = client.principal()
calendars = my_principal.calendars()
calendar = my_principal.calendar(cal_id=cal_id)
events_fetched = calendar.date_search(
start=start_of_week, end=end_of_week, expand=False)
for id in [cal_id]:
calendar = my_principal.calendar(cal_id=id)
events += Event.fromCalDavEvents(calendar.date_search(
start=start_of_week, end=end_of_week, expand=False))
events_fetched_by_date = {}
for event in events_fetched:
value = event.vobject_instance.vevent.dtstart.value
if isinstance(value, datetime.datetime):
events_fetched_by_date[datetime.datetime.date(value)] = event
elif isinstance(value, datetime.date):
events_fetched_by_date[value] = event
else:
raise Exception
for url in [
'http://ical-cdn.teamsnap.com/team_schedule/5f1ddc9e-15b0-4912-84a2-11cc70e9e375.ics'
]:
r = requests.get(url)
c = cal.Calendar.from_ical(r.content)
events += Event.fromIcalendar(c)
days = []
for single_date in daterange(start_of_week, end_of_week):
event = events_fetched_by_date.get(single_date)
if event:
days.append((single_date, event.vobject_instance.vevent))
else:
days.append((single_date,[]))
days_events = [e for e in events if (e.dtstart.date() <= single_date <= e.dtend.date())]
days.append((single_date, days_events))
# breakpoint()
pass
# r = "<br>".join([event.vobject_instance.vevent.summary.value for event in events_fetched if event.vobject_instance.vevent.dtstart.value < datetime.now()])
return render_template("dashboard.html", days=days, today=datetime.datetime.now())
return render_template("dashboard.html",
days=days,
today=today)
if __name__ == '__main__':
app.run(host='0.0.0.0', port=81)