feat: add enable/disable toggle for chore scheduling in ScheduleModal
All checks were successful
Chore App Build, Test, and Push Docker Images / build-and-push (push) Successful in 2m39s

- Introduced a toggle button to enable or disable chores in the scheduler.
- The toggle will be available in both types of schedulers.
- Added UI design proposal and considerations for mobile dimensions.
- Included E2E tests to ensure toggle state persistence and correct behavior in child view.
This commit is contained in:
2026-03-20 16:42:13 -04:00
parent db6e0a7ce8
commit ef9cb01d92
45 changed files with 3543 additions and 232 deletions

View File

@@ -319,3 +319,96 @@ def test_extend_chore_time_missing_date(client):
def test_extend_chore_time_bad_child(client):
resp = client.post('/child/bad-child/task/bad-task/extend', json={"date": "2025-01-15"})
assert resp.status_code == 404
# ---------------------------------------------------------------------------
# enabled field
# ---------------------------------------------------------------------------
def test_create_schedule_enabled_by_default(client):
"""Omitting 'enabled' should persist as True."""
payload = {"mode": "days", "day_configs": [{"day": 1, "hour": 8, "minute": 0}]}
resp = client.put(f'/child/{TEST_CHILD_ID}/task/{TEST_TASK_ID}/schedule', json=payload)
assert resp.status_code == 200
assert resp.get_json()["enabled"] is True
def test_create_schedule_with_enabled_false(client):
"""Explicitly setting enabled=False persists correctly."""
payload = {
"mode": "days",
"day_configs": [{"day": 1, "hour": 8, "minute": 0}],
"enabled": False,
}
resp = client.put(f'/child/{TEST_CHILD_ID}/task/{TEST_TASK_ID}/schedule', json=payload)
assert resp.status_code == 200
assert resp.get_json()["enabled"] is False
def test_update_schedule_toggle_enabled(client):
"""Toggle enabled off, then back on; both changes persist."""
base = {"mode": "days", "day_configs": [{"day": 2, "hour": 9, "minute": 0}]}
r1 = client.put(f'/child/{TEST_CHILD_ID}/task/{TEST_TASK_ID}/schedule', json={**base, "enabled": True})
assert r1.get_json()["enabled"] is True
r2 = client.put(f'/child/{TEST_CHILD_ID}/task/{TEST_TASK_ID}/schedule', json={**base, "enabled": False})
assert r2.get_json()["enabled"] is False
r3 = client.put(f'/child/{TEST_CHILD_ID}/task/{TEST_TASK_ID}/schedule', json={**base, "enabled": True})
assert r3.get_json()["enabled"] is True
def test_enabled_field_in_get_response(client):
"""GET response includes the 'enabled' field."""
payload = {"mode": "interval", "interval_days": 2, "anchor_date": "", "enabled": False}
client.put(f'/child/{TEST_CHILD_ID}/task/{TEST_TASK_ID}/schedule', json=payload)
resp = client.get(f'/child/{TEST_CHILD_ID}/task/{TEST_TASK_ID}/schedule')
assert resp.status_code == 200
data = resp.get_json()
assert "enabled" in data
assert data["enabled"] is False
def test_enabled_invalid_value_returns_400(client):
"""Non-boolean value for enabled returns 400."""
payload = {"mode": "days", "day_configs": [], "enabled": "yes"}
resp = client.put(f'/child/{TEST_CHILD_ID}/task/{TEST_TASK_ID}/schedule', json=payload)
assert resp.status_code == 400
# ---------------------------------------------------------------------------
# ChoreSchedule model: enabled serialization
# ---------------------------------------------------------------------------
def test_chore_schedule_from_dict_defaults_enabled():
"""from_dict without 'enabled' defaults to True."""
from models.chore_schedule import ChoreSchedule
s = ChoreSchedule.from_dict({
"child_id": "c1", "task_id": "t1", "mode": "days",
"day_configs": [], "interval_days": 2, "anchor_date": "",
"interval_has_deadline": True, "interval_hour": 0, "interval_minute": 0,
})
assert s.enabled is True
def test_chore_schedule_from_dict_enabled_false():
"""from_dict with enabled=False preserves the value."""
from models.chore_schedule import ChoreSchedule
s = ChoreSchedule.from_dict({
"child_id": "c1", "task_id": "t1", "mode": "days",
"day_configs": [], "interval_days": 2, "anchor_date": "",
"interval_has_deadline": True, "interval_hour": 0, "interval_minute": 0,
"enabled": False,
})
assert s.enabled is False
def test_chore_schedule_to_dict_includes_enabled():
"""to_dict includes the 'enabled' key with the correct value."""
from models.chore_schedule import ChoreSchedule
s = ChoreSchedule(child_id="c1", task_id="t1", mode="days", enabled=False)
d = s.to_dict()
assert "enabled" in d
assert d["enabled"] is False