From a9829078cce3789e010d33b193842da126531d24 Mon Sep 17 00:00:00 2001
From: Pierrick Brun
Date: Mon, 16 Dec 2024 17:42:13 +0100
Subject: [PATCH] fix: :bug: make everything work with rrulesets
---
rq_scheduler/utils.py | 6 +++---
tests/test_scheduler.py | 18 ++++++++++++++++++
2 files changed, 21 insertions(+), 3 deletions(-)
diff --git a/rq_scheduler/utils.py b/rq_scheduler/utils.py
index c9ee40c..4fbd404 100644
--- a/rq_scheduler/utils.py
+++ b/rq_scheduler/utils.py
@@ -36,12 +36,12 @@ def get_next_rrule_scheduled_time(rrule_string):
"""Calculate the next scheduled time by creating a rrule object
with a rrule string"""
timezone = dateutil.tz.UTC
- rule = dateutil.rrule.rrulestr(rrule_string)
- if rule._dtstart.tzinfo is None:
+ ruleset = dateutil.rrule.rrulestr(rrule_string, forceset=True)
+ if ruleset[0].tzinfo is None:
now = datetime.now() # naive datetime
else:
now = datetime.now(tz=timezone) # aware datetime
- next_time = rule.after(now)
+ next_time = ruleset.after(now)
return next_time.astimezone(timezone)
diff --git a/tests/test_scheduler.py b/tests/test_scheduler.py
index 9d29d03..a98a504 100644
--- a/tests/test_scheduler.py
+++ b/tests/test_scheduler.py
@@ -1125,3 +1125,21 @@ def test_rrule_persisted_correctly_with_until(self):
assert datetime_time.minute == 1
assert datetime_time.second == 0
assert datetime_time - now <= timedelta(hours=1), f"{datetime_time - now} is greater than 1 hour"
+
+ def test_rruleset_persisted_correctly_with_dtstart(self):
+ """
+ Ensure that rrule attribute gets correctly saved in Redis.
+ """
+ # create a job that runs one minute past each whole hour
+ job = self.scheduler.rrule("DTSTART:20241126T154900Z\nRRULE:FREQ=HOURLY;WKST=MO;BYMINUTE=1;BYSECOND=0\nRRULE:FREQ=MINUTELY;INTERVAL=5;COUNT=2", say_hello)
+ job_from_queue = Job.fetch(job.id, connection=self.testconn)
+ self.assertEqual(job_from_queue.meta['rrule_string'], "DTSTART:20241126T154900Z\nRRULE:FREQ=HOURLY;WKST=MO;BYMINUTE=1;BYSECOND=0\nRRULE:FREQ=MINUTELY;INTERVAL=5;COUNT=2")
+
+ # get the scheduled_time and convert it to a datetime object
+ unix_time = self.testconn.zscore(self.scheduler.scheduled_jobs_key, job.id)
+ datetime_time = from_unix(unix_time)
+
+ # check that minute=1, seconds=0, and is within an hour
+ assert datetime_time.minute == 1
+ assert datetime_time.second == 0
+ assert datetime_time - datetime.utcnow() <= timedelta(hours=1), f"{datetime_time - datetime.utcnow()} is greater than 1 hour"
\ No newline at end of file