Skip to content

Commit 989335a

Browse files
committed
Silently clear schedule_config for non-batch triggers
1 parent 0fe71a9 commit 989335a

File tree

3 files changed

+58
-4
lines changed

3 files changed

+58
-4
lines changed

posthog/api/hog_flow.py

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -328,8 +328,14 @@ def validate(self, data):
328328
if "bytecode" not in data["conversion"]:
329329
data["conversion"]["bytecode"] = []
330330

331-
# Validate schedule_config if present and not a draft
331+
# Silently clear schedule_config for trigger types that don't support scheduling
332+
SCHEDULABLE_TRIGGER_TYPES = {"batch"}
332333
schedule_config = data.get("schedule_config")
334+
if schedule_config and data["trigger"].get("type") not in SCHEDULABLE_TRIGGER_TYPES:
335+
data["schedule_config"] = None
336+
schedule_config = None
337+
338+
# Validate schedule_config if present and not a draft
333339
if schedule_config and not self.context.get("is_draft"):
334340
rrule_str = schedule_config.get("rrule")
335341
if not rrule_str:

products/workflows/backend/test/test_hog_flow_schedule.py

Lines changed: 49 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -17,8 +17,15 @@
1717
"filters": {"properties": [{"key": "$browser", "type": "person", "value": ["Chrome"], "operator": "exact"}]},
1818
}
1919

20+
EVENT_TRIGGER = {
21+
"type": "event",
22+
"filters": {
23+
"events": [{"id": "$pageview", "name": "$pageview", "type": "events", "order": 0}],
24+
},
25+
}
26+
2027

21-
def _make_workflow_payload(workflow_status="draft", schedule_config=None):
28+
def _make_workflow_payload(workflow_status="draft", schedule_config=None, trigger_config=None):
2229
payload = {
2330
"name": "Test Batch Workflow",
2431
"status": workflow_status,
@@ -27,7 +34,7 @@ def _make_workflow_payload(workflow_status="draft", schedule_config=None):
2734
"id": "trigger_node",
2835
"name": "trigger",
2936
"type": "trigger",
30-
"config": BATCH_TRIGGER,
37+
"config": trigger_config or BATCH_TRIGGER,
3138
}
3239
],
3340
}
@@ -356,3 +363,43 @@ def test_schedule_with_timezone_stores_timezone(self):
356363
hog_flow = HogFlow.objects.get(id=workflow["id"])
357364
assert hog_flow.schedule_config is not None
358365
assert hog_flow.schedule_config["timezone"] == "US/Eastern"
366+
367+
def test_schedule_config_cleared_for_non_batch_trigger(self):
368+
schedule_config = {
369+
"rrule": "FREQ=WEEKLY;INTERVAL=1;BYDAY=MO",
370+
"starts_at": "2030-01-01T09:00:00.000Z",
371+
}
372+
payload = _make_workflow_payload(
373+
workflow_status="active",
374+
schedule_config=schedule_config,
375+
trigger_config=EVENT_TRIGGER,
376+
)
377+
response = self.client.post(f"/api/projects/{self.team.id}/hog_flows", payload)
378+
assert response.status_code == status.HTTP_201_CREATED
379+
380+
hog_flow = HogFlow.objects.get(id=response.json()["id"])
381+
assert hog_flow.schedule_config is None
382+
assert HogFlowScheduledRun.objects.filter(hog_flow=hog_flow, status="pending").count() == 0
383+
384+
def test_switching_from_batch_to_event_trigger_clears_schedule_and_pending_run(self):
385+
schedule_config = {
386+
"rrule": "FREQ=WEEKLY;INTERVAL=1;BYDAY=MO",
387+
"starts_at": "2030-01-01T09:00:00.000Z",
388+
}
389+
workflow = self._create_batch_workflow(schedule_config=schedule_config)
390+
hog_flow = HogFlow.objects.get(id=workflow["id"])
391+
assert hog_flow.schedule_config is not None
392+
assert HogFlowScheduledRun.objects.filter(hog_flow=hog_flow, status="pending").count() == 1
393+
394+
# Switch to event trigger
395+
payload = _make_workflow_payload(
396+
workflow_status="active",
397+
schedule_config=schedule_config,
398+
trigger_config=EVENT_TRIGGER,
399+
)
400+
response = self.client.patch(f"/api/projects/{self.team.id}/hog_flows/{workflow['id']}", payload)
401+
assert response.status_code == status.HTTP_200_OK
402+
403+
hog_flow.refresh_from_db()
404+
assert hog_flow.schedule_config is None
405+
assert HogFlowScheduledRun.objects.filter(hog_flow=hog_flow, status="pending").count() == 0

products/workflows/backend/utils/schedule_sync.py

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -22,7 +22,8 @@ def sync_schedule(hog_flow: HogFlow, team_id: int) -> None:
2222
HogFlowScheduledRun.objects.filter(hog_flow=hog_flow, status=HogFlowScheduledRun.Status.PENDING).delete()
2323

2424
schedule_config = hog_flow.schedule_config
25-
if not schedule_config or hog_flow.status != HogFlow.State.ACTIVE:
25+
trigger_type = (hog_flow.trigger or {}).get("type")
26+
if not schedule_config or hog_flow.status != HogFlow.State.ACTIVE or trigger_type != "batch":
2627
return
2728

2829
rrule_str = schedule_config.get("rrule")

0 commit comments

Comments
 (0)