Fix adding/updating todo items with due date in CalDAV integration (#105435)

* refactor: return date/datetime for due date

* fix: explicitly set due date on vTODO component

Using `set_due` automatically handles converting the Python-native
date/datetime values to the correct representation required by RFC5545.

* fix: fix tests with changed due date handling

* fix: item.due may not be a str

* refactor: keep local timezone of due datetime

* refactor: reorder import statement

To make ruff happy.

* fix: fix false-positive mypy error
This commit is contained in:
Florian B 2023-12-10 17:23:05 +01:00 committed by GitHub
parent 6a3c422d2f
commit 063ac53f01
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
2 changed files with 14 additions and 9 deletions

View file

@ -98,10 +98,7 @@ def _to_ics_fields(item: TodoItem) -> dict[str, Any]:
if status := item.status:
item_data["status"] = TODO_STATUS_MAP_INV.get(status, "NEEDS-ACTION")
if due := item.due:
if isinstance(due, datetime):
item_data["due"] = dt_util.as_utc(due).strftime("%Y%m%dT%H%M%SZ")
else:
item_data["due"] = due.strftime("%Y%m%d")
item_data["due"] = due
if description := item.description:
item_data["description"] = description
return item_data
@ -162,7 +159,10 @@ class WebDavTodoListEntity(TodoListEntity):
except (requests.ConnectionError, DAVError) as err:
raise HomeAssistantError(f"CalDAV lookup error: {err}") from err
vtodo = todo.icalendar_component # type: ignore[attr-defined]
vtodo.update(**_to_ics_fields(item))
updated_fields = _to_ics_fields(item)
if "due" in updated_fields:
todo.set_due(updated_fields.pop("due")) # type: ignore[attr-defined]
vtodo.update(**updated_fields)
try:
await self.hass.async_add_executor_job(
partial(

View file

@ -1,4 +1,5 @@
"""The tests for the webdav todo component."""
from datetime import UTC, date, datetime
from typing import Any
from unittest.mock import MagicMock, Mock
@ -200,12 +201,16 @@ async def test_supported_components(
),
(
{"due_date": "2023-11-18"},
{"status": "NEEDS-ACTION", "summary": "Cheese", "due": "20231118"},
{"status": "NEEDS-ACTION", "summary": "Cheese", "due": date(2023, 11, 18)},
{**RESULT_ITEM, "due": "2023-11-18"},
),
(
{"due_datetime": "2023-11-18T08:30:00-06:00"},
{"status": "NEEDS-ACTION", "summary": "Cheese", "due": "20231118T143000Z"},
{
"status": "NEEDS-ACTION",
"summary": "Cheese",
"due": datetime(2023, 11, 18, 14, 30, 00, tzinfo=UTC),
},
{**RESULT_ITEM, "due": "2023-11-18T08:30:00-06:00"},
),
(
@ -311,13 +316,13 @@ async def test_add_item_failure(
),
(
{"due_date": "2023-11-18"},
["SUMMARY:Cheese", "DUE:20231118"],
["SUMMARY:Cheese", "DUE;VALUE=DATE:20231118"],
"1",
{**RESULT_ITEM, "due": "2023-11-18"},
),
(
{"due_datetime": "2023-11-18T08:30:00-06:00"},
["SUMMARY:Cheese", "DUE:20231118T143000Z"],
["SUMMARY:Cheese", "DUE;TZID=America/Regina:20231118T083000"],
"1",
{**RESULT_ITEM, "due": "2023-11-18T08:30:00-06:00"},
),