ci: run pre-commit manually and apply linters

pull/97/head
Martin Eigenmann 2021-12-27 07:22:37 +01:00
rodzic 93187a5ec6
commit d6bf733597
Nie znaleziono w bazie danych klucza dla tego podpisu
ID klucza GPG: 069D1EE3806CA368
3 zmienionych plików z 178 dodań i 154 usunięć

Wyświetl plik

@ -22,7 +22,7 @@ def events(
http=None,
tzinfo=None,
sort=None,
strict=False
strict=False,
):
"""
Get all events form the given iCal URL occurring in the given time range.
@ -52,7 +52,9 @@ def events(
if not content and string_content:
content = ical_download.data_from_string(string_content, apple_fix=fix_apple)
found_events += parse_events(content, start=start, end=end, tzinfo=tzinfo, sort=sort, strict=strict)
found_events += parse_events(
content, start=start, end=end, tzinfo=tzinfo, sort=sort, strict=strict
)
return found_events

Wyświetl plik

@ -17,6 +17,7 @@ from uuid import uuid4
from icalendar.windows_to_olson import WINDOWS_TO_OLSON
from pytz import timezone
def now():
"""
Get current time.
@ -102,20 +103,19 @@ class Event:
elif type(self.start) is datetime and type(other.start) is date:
return self.start.date() < other.start
def __str__(self):
return "%s: %s (%s)" % (self.start, self.summary, self.end - self.start)
def astimezone(self, tzinfo):
if type(self.start) is datetime:
self.start = self.start.astimezone(tzinfo)
if type(self.end) is datetime:
self.end = self.end.astimezone(tzinfo)
return self
def copy_to(self, new_start=None, uid=None):
"""
Create a new event equal to this with new start date.
@ -226,7 +226,7 @@ def create_event(component, utc_default):
if component.get("RECURRENCE-ID"):
rid = component.get("RECURRENCE-ID").dt
# Spec defines that if DTSTART is a date RECURRENCE-ID also is to be interpreted as a date
if type(component.get("dtstart").dt) is date:
event.recurrence_id = date(year=rid.year, month=rid.month, day=rid.day)
@ -258,7 +258,15 @@ def create_event(component, utc_default):
return event
def parse_events(content, start=None, end=None, default_span=timedelta(days=7), tzinfo=None, sort=False, strict=False):
def parse_events(
content,
start=None,
end=None,
default_span=timedelta(days=7),
tzinfo=None,
sort=False,
strict=False,
):
"""
Query the events occurring in a given time range.
@ -278,13 +286,12 @@ def parse_events(content, start=None, end=None, default_span=timedelta(days=7),
raise ValueError("Content is invalid!")
calendar = Calendar.from_ical(content)
# > Will be deprecated ========================
# Calendar.from_ical already parses timezones as specified in the ical.
# We can specify a 'default' tz but this is not according to spec.
# Kept this here to verify tests and backward compatibility
# Keep track of the timezones defined in the calendar
timezones = {}
@ -313,9 +320,9 @@ def parse_events(content, start=None, end=None, default_span=timedelta(days=7),
utc_default = True
cal_tz = UTC
# < ==========================================
found = []
def add_if_not_exception(event):
exdate = "%04d%02d%02d" % (
event.start.year,
@ -325,10 +332,10 @@ def parse_events(content, start=None, end=None, default_span=timedelta(days=7),
if exdate not in exceptions:
found.append(event)
for component in calendar.walk():
for component in calendar.walk():
exceptions = {}
if "EXDATE" in component:
# Deal with the fact that sometimes it's a list and
# sometimes it's a singleton
@ -340,19 +347,25 @@ def parse_events(content, start=None, end=None, default_span=timedelta(days=7),
for ex in exlist:
exdate = ex.to_ical().decode("UTF-8")
exceptions[exdate[0:8]] = exdate
if component.name == "VEVENT":
e = create_event(component, utc_default)
# make rule.between happy and provide from, to points in time that have the same format as dtstart
s = component['dtstart'].dt
s = component["dtstart"].dt
if type(s) is date and not e.recurring:
f, t = date(start.year, start.month, start.day), date(end.year, end.month, end.day)
f, t = date(start.year, start.month, start.day), date(
end.year, end.month, end.day
)
elif type(s) is datetime and s.tzinfo:
f, t = datetime(start.year, start.month, start.day, tzinfo=s.tzinfo), datetime(end.year, end.month, end.day, tzinfo=s.tzinfo)
f, t = datetime(
start.year, start.month, start.day, tzinfo=s.tzinfo
), datetime(end.year, end.month, end.day, tzinfo=s.tzinfo)
else:
f, t = datetime(start.year, start.month, start.day), datetime(end.year, end.month, end.day)
f, t = datetime(start.year, start.month, start.day), datetime(
end.year, end.month, end.day
)
if e.recurring:
rule = parse_rrule(component)
for dt in rule.between(f, t, inc=True):
@ -361,18 +374,18 @@ def parse_events(content, start=None, end=None, default_span=timedelta(days=7),
# recurrence has crossed over the daylight savings time boundary.
if type(dt) is datetime and dt.tzinfo:
dtstart = dt.replace(tzinfo=get_timezone(str(dt.tzinfo)))
ecopy = e.copy_to(dtstart.date() if type(s) is date else dtstart, e.uid)
ecopy = e.copy_to(
dtstart.date() if type(s) is date else dtstart, e.uid
)
else:
ecopy = e.copy_to(dt.date() if type(s) is date else dt, e.uid)
add_if_not_exception(ecopy)
elif e.end >= f and e.start <= t:
add_if_not_exception(e)
result = found.copy()
# Remove events that are replaced in ical
for event in found:
if not event.recurrence_id and (event.uid, event.start) in [
@ -386,8 +399,22 @@ def parse_events(content, start=None, end=None, default_span=timedelta(days=7),
if not strict:
for event in result:
if type(event.start) is date:
event.start = datetime(year=event.start.year, month=event.start.month, day=event.start.day, hour=0, minute=0, tzinfo=cal_tz)
event.end = datetime(year=event.end.year, month=event.end.month, day=event.end.day, hour=0, minute=0, tzinfo=cal_tz)
event.start = datetime(
year=event.start.year,
month=event.start.month,
day=event.start.day,
hour=0,
minute=0,
tzinfo=cal_tz,
)
event.end = datetime(
year=event.end.year,
month=event.end.month,
day=event.end.day,
hour=0,
minute=0,
tzinfo=cal_tz,
)
elif type(event.start) is datetime:
if event.start.tzinfo:
event.start = event.start.astimezone(cal_tz)
@ -395,19 +422,33 @@ def parse_events(content, start=None, end=None, default_span=timedelta(days=7),
else:
event.start = event.start.replace(tzinfo=cal_tz)
event.end = event.end.replace(tzinfo=cal_tz)
if event.created:
if event.created:
if type(event.created) is date:
event.created = datetime(year=event.created.year, month=event.created.month, day=event.created.day, hour=0, minute=0, tzinfo=cal_tz)
event.created = datetime(
year=event.created.year,
month=event.created.month,
day=event.created.day,
hour=0,
minute=0,
tzinfo=cal_tz,
)
if type(event.created) is datetime:
if event.created.tzinfo:
event.created = event.created.astimezone(cal_tz)
else:
event.created = event.created.replace(tzinfo=cal_tz)
if event.last_modified:
if event.last_modified:
if type(event.last_modified) is date:
event.last_modified = datetime(year=event.last_modified.year, month=event.last_modified.month, day=event.last_modified.day, hour=0, minute=0, tzinfo=cal_tz)
event.last_modified = datetime(
year=event.last_modified.year,
month=event.last_modified.month,
day=event.last_modified.day,
hour=0,
minute=0,
tzinfo=cal_tz,
)
if type(event.last_modified) is datetime:
if event.last_modified.tzinfo:
event.last_modified = event.last_modified.astimezone(cal_tz)
@ -417,12 +458,10 @@ def parse_events(content, start=None, end=None, default_span=timedelta(days=7),
if sort:
result.sort()
if tzinfo:
result = [event.astimezone(tzinfo) for event in result]
return result
@ -435,43 +474,51 @@ def parse_rrule(component):
:param component: icalendar component
:return: extracted rrule or rruleset or None
"""
if not component.get("rrule"):
return None
dtstart = component.get("dtstart").dt
# component['rrule'] can be both a scalar and a list
rrules = component.get("rrule")
if not isinstance(rrules, list):
rrules = [rrules]
def conform_until(until, dtstart):
if type(dtstart) is datetime:
return (until.astimezone(UTC) if type(until) is datetime else datetime(year=until.year, month=until.month, day=until.day, tzinfo=UTC)) + dtstart.tzinfo.utcoffset(dtstart)
return (
until.astimezone(UTC)
if type(until) is datetime
else datetime(
year=until.year, month=until.month, day=until.day, tzinfo=UTC
)
) + dtstart.tzinfo.utcoffset(dtstart)
elif type(dtstart) is date:
return until.date() + timedelta(days=1) if type(until) is datetime else until
return (
until.date() + timedelta(days=1) if type(until) is datetime else until
)
for index, rru in enumerate(rrules):
if "UNTIL" in rru:
rrules[index]["UNTIL"] = [
conform_until(until, dtstart) for until in rrules[index]["UNTIL"]
]
rule = rrulestr(
"\n".join(x.to_ical().decode() for x in rrules),
dtstart=dtstart,
forceset=True,
unfold=True,
)
"\n".join(x.to_ical().decode() for x in rrules),
dtstart=dtstart,
forceset=True,
unfold=True,
)
if component.get("exdate"):
# Add exdates to the rruleset
for exd in extract_exdates(component):
if type(dtstart) is date:
if exd.tzinfo:
rule.exdate(exd.replace(tzinfo=None))
#rule.exdate(datetime(year=exd.year, month=exd.month, day=exd.day) + timedelta(days=1))
# rule.exdate(datetime(year=exd.year, month=exd.month, day=exd.day) + timedelta(days=1))
else:
rule.exdate(exd)
else:
@ -479,12 +526,12 @@ def parse_rrule(component):
# TODO: What about rdates and exrules?
if component.get("exrule"):
#pass
print('exrule', component.get("exrule"))
# pass
print("exrule", component.get("exrule"))
if component.get("rdate"):
#pass
print('rdate', component.get("rdate"))
# pass
print("rdate", component.get("rdate"))
return rule
@ -511,4 +558,4 @@ def get_timezone(tz_name):
if tz_name in WINDOWS_TO_OLSON:
return gettz(WINDOWS_TO_OLSON[tz_name])
else:
return gettz(tz_name)
return gettz(tz_name)

Wyświetl plik

@ -288,7 +288,6 @@ class ICalEventsTests(unittest.TestCase):
self.assertTrue(icalevents.all_done(key), "request is finished")
self.assertEqual(len(icalevents.latest_events(key)), 2, "two events are found")
def test_events_no_description(self):
ical = "test/test_data/no_description.ics"
start = date(2018, 10, 15)
@ -368,7 +367,7 @@ class ICalEventsTests(unittest.TestCase):
evs = icalevents.events(file=ical, start=start, end=end, sort=True)
self.assertEqual(len(evs), 42, "42 events in total - one was moved")
def test_recurence_id_ms_moved(self):
ical = "test/test_data/recurrenceid_ms.ics"
start = date(2021, 4, 8)
@ -395,9 +394,7 @@ class ICalEventsTests(unittest.TestCase):
evs = icalevents.events(file=ical, start=start, end=end)
self.assertEqual(
len(evs), 239, "239 events in total"
)
self.assertEqual(len(evs), 239, "239 events in total")
def test_cest_2021_02(self):
ical = "test/test_data/cest.ics"
@ -406,7 +403,7 @@ class ICalEventsTests(unittest.TestCase):
evs = icalevents.events(file=ical, start=start, end=end)
self.assertEqual(len(evs), 17, "17 in february")
def test_cest_2021_03(self):
ical = "test/test_data/cest.ics"
start = date(2021, 3, 1)
@ -419,62 +416,53 @@ class ICalEventsTests(unittest.TestCase):
ical = "test/test_data/cest.ics"
start = date(2021, 4, 1)
end = date(2021, 5, 1)
tz = gettz('Europe/Zurich')
events = icalevents.events(file=ical, start=start, end=end, tzinfo=tz, sort=True, strict=True)
tz = gettz("Europe/Zurich")
events = icalevents.events(
file=ical, start=start, end=end, tzinfo=tz, sort=True, strict=True
)
times = [
((2021, 4, 1, 14, 0), (2021, 4, 1, 14, 30)),
((2021, 4, 1, 15, 30), (2021, 4, 1, 17, 0)),
((2021, 4, 2), (2021, 4, 3)),
((2021, 4, 5, 16, 00), (2021, 4, 5, 17, 0)),
((2021, 4, 7), (2021, 4, 8)),
((2021, 4, 8, 11, 0), (2021, 4, 8, 12, 0)),
((2021, 4, 8, 14, 30), (2021, 4, 8, 15, 0)),
((2021, 4, 8, 15, 0), (2021, 4, 8, 15, 30)),
((2021, 4, 9), (2021, 4, 10)),
#((2021, 4, 9), (2021, 4, 10)), # Google said this should exist, microsoft disagrees
# ((2021, 4, 9), (2021, 4, 10)), # Google said this should exist, microsoft disagrees
((2021, 4, 12, 11, 0), (2021, 4, 12, 11, 30)),
((2021, 4, 12, 16, 0), (2021, 4, 12, 17, 0)),
((2021, 4, 14), (2021, 4, 15)),
((2021, 4, 15, 12, 0), (2021, 4, 15, 13, 0)),
((2021, 4, 15, 15, 0), (2021, 4, 15, 15, 30)),
((2021, 4, 16), (2021, 4, 17)),
((2021, 4, 19, 16, 0), (2021, 4, 19, 17, 0)),
((2021, 4, 21), (2021, 4, 22)),
((2021, 4, 22, 11, 0), (2021, 4, 22, 12, 0)),
((2021, 4, 22, 14, 45), (2021, 4, 22, 15, 15)),
((2021, 4, 23), (2021, 4, 24)),
((2021, 4, 26, 16, 0), (2021, 4, 26, 17, 0)),
((2021, 4, 28), (2021, 4, 29)),
((2021, 4, 29, 9, 0), (2021, 4, 29, 11, 0)),
((2021, 4, 29, 11, 0), (2021, 4, 29, 11, 30)),
((2021, 4, 29, 14, 15), (2021, 4, 29, 15, 00)),
((2021, 4, 29, 15, 0), (2021, 4, 29, 15, 30)),
((2021, 4, 30), (2021, 5, 1)),
]
for index, time in enumerate(times):
self.assertEqual(events[index].start, date(*time[0]) if len(time[0]) == 3 else datetime(*time[0], tzinfo=tz))
self.assertEqual(events[index].end, date(*time[1]) if len(time[1]) == 3 else datetime(*time[1], tzinfo=tz))
self.assertEqual(
events[index].start,
date(*time[0]) if len(time[0]) == 3 else datetime(*time[0], tzinfo=tz),
)
self.assertEqual(
events[index].end,
date(*time[1]) if len(time[1]) == 3 else datetime(*time[1], tzinfo=tz),
)
self.assertEqual(len(events), len(times))
def test_cest_2021_05(self):
@ -482,52 +470,44 @@ class ICalEventsTests(unittest.TestCase):
start = date(2021, 5, 1)
end = date(2021, 6, 1)
tz = gettz('Europe/Zurich')
events = icalevents.events(file=ical, start=start, end=end, tzinfo=tz, sort=True, strict=True)
tz = gettz("Europe/Zurich")
events = icalevents.events(
file=ical, start=start, end=end, tzinfo=tz, sort=True, strict=True
)
times = [
((2021, 5, 3, 16, 0), (2021, 5, 3, 17, 0)),
((2021, 5, 5), (2021, 5, 6)),
((2021, 5, 6, 11, 0), (2021, 5, 6, 12, 0)),
((2021, 5, 6, 15, 0), (2021, 5, 6, 15, 30)),
((2021, 5, 7), (2021, 5, 8)),
((2021, 5, 10, 16, 0), (2021, 5, 10, 17, 0)),
((2021, 5, 12), (2021, 5, 13)),
((2021, 5, 13, 15, 0), (2021, 5, 13, 15, 30)),
((2021, 5, 14), (2021, 5, 15)),
((2021, 5, 17, 16, 0), (2021, 5, 17, 17, 0)),
((2021, 5, 19), (2021, 5, 20)),
((2021, 5, 20, 11, 0), (2021, 5, 20, 12, 0)),
((2021, 5, 20, 12, 0), (2021, 5, 20, 13, 0)),
((2021, 5, 20, 15, 0), (2021, 5, 20, 15, 30)),
((2021, 5, 21), (2021, 5, 22)),
((2021, 5, 24, 16, 0), (2021, 5, 24, 17, 0)),
((2021, 5, 26), (2021, 5, 27)),
((2021, 5, 27, 15, 0), (2021, 5, 27, 15, 30)),
((2021, 5, 28), (2021, 5, 29)),
((2021, 5, 31, 16, 0), (2021, 5, 31, 17, 0)),
]
for index, time in enumerate(times):
self.assertEqual(events[index].start, date(*time[0]) if len(time[0]) == 3 else datetime(*time[0], tzinfo=tz))
self.assertEqual(events[index].end, date(*time[1]) if len(time[1]) == 3 else datetime(*time[1], tzinfo=tz))
self.assertEqual(
events[index].start,
date(*time[0]) if len(time[0]) == 3 else datetime(*time[0], tzinfo=tz),
)
self.assertEqual(
events[index].end,
date(*time[1]) if len(time[1]) == 3 else datetime(*time[1], tzinfo=tz),
)
self.assertEqual(len(events), len(times))
def test_cest_2021_06(self):
@ -537,7 +517,7 @@ class ICalEventsTests(unittest.TestCase):
evs = icalevents.events(file=ical, start=start, end=end)
self.assertEqual(len(evs), 11, "11 in june")
def test_cest_2021_07(self):
ical = "test/test_data/cest.ics"
start = date(2021, 7, 1)
@ -545,7 +525,7 @@ class ICalEventsTests(unittest.TestCase):
evs = icalevents.events(file=ical, start=start, end=end)
self.assertEqual(len(evs), 1, "1 in july")
def test_cest_1(self):
ical = "test/test_data/cest_every_day_for_one_year.ics"
start = date(2020, 1, 1)
@ -706,98 +686,93 @@ class ICalEventsTests(unittest.TestCase):
start = date(2021, 8, 30)
end = date(2021, 9, 18)
tz = gettz('Europe/Zurich')
events = icalevents.events(file=ical, start=start, end=end, tzinfo=tz, sort=True, strict=True)
tz = gettz("Europe/Zurich")
events = icalevents.events(
file=ical, start=start, end=end, tzinfo=tz, sort=True, strict=True
)
times = [
((2021, 8, 30, 8, 0), (2021, 8, 30, 17, 0)),
((2021, 8, 30, 9, 30), (2021, 8, 30, 10, 0)),
((2021, 8, 31, 10, 0), (2021, 8, 31, 10, 30)),
((2021, 8, 31, 10, 15), (2021, 8, 31, 10, 45)),
((2021, 8, 31, 13, 15), (2021, 8, 31, 14, 0)),
((2021, 9, 1, 9, 0), (2021, 9, 1, 10, 0)),
((2021, 9, 1, 9, 30), (2021, 9, 1, 10, 0)),
((2021, 9, 1, 12, 0), (2021, 9, 1, 13, 0)),
((2021, 9, 2, 10, 0), (2021, 9, 2, 10, 30)),
((2021, 9, 3, 8, 0), (2021, 9, 3, 8, 30)),
((2021, 9, 3, 9, 0), (2021, 9, 3, 9, 30)),
((2021, 9, 3, 9, 30), (2021, 9, 3, 10, 0)),
((2021, 9, 3, 15, 30), (2021, 9, 3, 16, 0)),
((2021, 9, 3, 17, 30), (2021, 9, 3, 19, 0)),
((2021, 9, 6, 8, 0), (2021, 9, 6, 17, 0)),
((2021, 9, 6, 9, 30), (2021, 9, 6, 10, 0)),
((2021, 9, 7, 9, 0), (2021, 9, 7, 12, 0)),
((2021, 9, 7, 9, 0), (2021, 9, 7, 12, 0)),
((2021, 9, 7, 10, 0), (2021, 9, 7, 10, 30)),
((2021, 9, 8, 9, 30), (2021, 9, 8, 10, 0)),
((2021, 9, 8, 12, 0), (2021, 9, 8, 13, 0)),
((2021, 9, 9), (2021, 9, 10)),
((2021, 9, 9, 10, 0), (2021, 9, 9, 10, 30)),
((2021, 9, 9, 11, 0), (2021, 9, 9, 12, 0)),
((2021, 9, 10, 8, 0), (2021, 9, 10, 8, 30)),
((2021, 9, 10, 9, 30), (2021, 9, 10, 10, 0)),
((2021, 9, 10, 17, 30), (2021, 9, 10, 19, 0)),
((2021, 9, 13, 9, 30), (2021, 9, 13, 10, 0)),
((2021, 9, 14, 9, 0), (2021, 9, 14, 10, 0)),
((2021, 9, 14, 10, 0), (2021, 9, 14, 10, 30)),
((2021, 9, 14, 15, 0), (2021, 9, 14, 15, 30)),
((2021, 9, 15, 9, 30), (2021, 9, 15, 10, 0)),
((2021, 9, 16, 10, 0), (2021, 9, 16, 10, 30)),
((2021, 9, 16), (2021, 9, 17)),
((2021, 9, 17, 9, 30), (2021, 9, 17, 10, 0)),
((2021, 9, 17, 17, 30), (2021, 9, 17, 19, 0)),
]
for index, time in enumerate(times):
self.assertEqual(events[index].start, date(*time[0]) if len(time[0]) == 3 else datetime(*time[0], tzinfo=tz))
self.assertEqual(events[index].end, date(*time[1]) if len(time[1]) == 3 else datetime(*time[1], tzinfo=tz))
self.assertEqual(
events[index].start,
date(*time[0]) if len(time[0]) == 3 else datetime(*time[0], tzinfo=tz),
)
self.assertEqual(
events[index].end,
date(*time[1]) if len(time[1]) == 3 else datetime(*time[1], tzinfo=tz),
)
self.assertEqual(len(events), len(times))
def test_recurring_tz_passover_spring(self):
ical = "test/test_data/recurring_override.ics"
start = date(2022, 3, 6)
end = date(2022, 4, 10)
tz = gettz('Europe/Zurich')
events = icalevents.events(file=ical, start=start, end=end, tzinfo=tz, sort=True, strict=True)
tz = gettz("Europe/Zurich")
events = icalevents.events(
file=ical, start=start, end=end, tzinfo=tz, sort=True, strict=True
)
times = [
((2022, 3, 8, 11, 45), (2022, 3, 8, 12, 0)),
((2022, 3, 10), (2022, 3, 11)),
((2022, 3, 10, 11, 0), (2022, 3, 10, 12, 0)),
((2022, 3, 15, 11, 45), (2022, 3, 15, 12, 0)),
((2022, 3, 22, 11, 45), (2022, 3, 22, 12, 0)),
((2022, 3, 22, 14, 00), (2022, 3, 22, 15, 0)),
((2022, 3, 24), (2022, 3, 25)),
((2022, 3, 29, 11, 45), (2022, 3, 29, 12, 0)),
((2022, 4, 3, 8, 0), (2022, 4, 3, 8, 30)),
((2022, 4, 7), (2022, 4, 8)),
]
for index, time in enumerate(times):
self.assertEqual(events[index].start, date(*time[0]) if len(time[0]) == 3 else datetime(*time[0], tzinfo=tz))
self.assertEqual(events[index].end, date(*time[1]) if len(time[1]) == 3 else datetime(*time[1], tzinfo=tz))
self.assertEqual(len(events), len(times))
self.assertEqual(
events[index].start,
date(*time[0]) if len(time[0]) == 3 else datetime(*time[0], tzinfo=tz),
)
self.assertEqual(
events[index].end,
date(*time[1]) if len(time[1]) == 3 else datetime(*time[1], tzinfo=tz),
)
self.assertEqual(len(events), len(times))