diff --git a/tests/__init__.py b/tests/__init__.py new file mode 100644 index 0000000..e69de29 diff --git a/tests/conftest.py b/tests/conftest.py new file mode 100644 index 0000000..22537ff --- /dev/null +++ b/tests/conftest.py @@ -0,0 +1,40 @@ +"""Fixtures for testing caldav2google.""" + +from unittest.mock import MagicMock + +import pytest + + +@pytest.fixture +def mock_google_service(): + """Create a mock Google Calendar service.""" + service = MagicMock() + events = MagicMock() + service.events.return_value = events + return service + + +@pytest.fixture +def mock_caldav_principal(): + """Create a mock CalDAV principal.""" + return MagicMock() + + +@pytest.fixture +def sample_event_data(): + """Create sample event data for testing.""" + return { + "test-uid-1": { + "uid": "test-uid-1", + "summary": "Test Event 1", + "description": "Test Description", + "location": "Test Location", + "start": "2024-01-01T10:00:00+00:00", + "end": "2024-01-01T11:00:00+00:00", + "last_modified": "2024-01-01T09:00:00+00:00", + "rrule": None, + "exdate": None, + "recurrence_id": None, + "google_event_id": "google-event-1", + }, + } diff --git a/tests/test_auth_google.py b/tests/test_auth_google.py new file mode 100644 index 0000000..0ccfe80 --- /dev/null +++ b/tests/test_auth_google.py @@ -0,0 +1,36 @@ +"""Tests for the auth_google module.""" + +import pytest + +from src.auth_google import search_calendar_id + + +def test_search_calendar_id_found(mock_google_service): + """Test searching for a calendar ID that exists in the list of calendars.""" + calendar_name = "Test Calendar" + calendars = { + "items": [ + {"summary": "Wrong Calendar", "id": "wrong-id"}, + {"summary": "Test Calendar", "id": "correct-id"}, + ], + } + mock_google_service.calendarList().list().execute.return_value = calendars + + result = search_calendar_id(mock_google_service, calendar_name) + + assert result == "correct-id" + + +def test_search_calendar_id_not_found(mock_google_service): + """Test searching for a calendar ID that does not exist in the list of calendars.""" + calendar_name = "Nonexistent Calendar" + calendars = { + "items": [ + {"summary": "Wrong Calendar", "id": "wrong-id"}, + {"summary": "Test Calendar", "id": "correct-id"}, + ], + } + mock_google_service.calendarList().list().execute.return_value = calendars + + with pytest.raises(ValueError, match=f"No calendar named '{calendar_name}' found"): + search_calendar_id(mock_google_service, calendar_name) diff --git a/tests/test_caldav_client.py b/tests/test_caldav_client.py new file mode 100644 index 0000000..6b74a4c --- /dev/null +++ b/tests/test_caldav_client.py @@ -0,0 +1,30 @@ +"""Tests for the caldav_client module.""" + +from unittest.mock import MagicMock + +import pytest + +from src.caldav_client import get_calendar + + +def test_get_calendar_found(mock_caldav_principal): + """Test getting a calendar that exists in the list of calendars.""" + calendar_name = "Test Calendar" + mock_calendar = MagicMock() + mock_calendar.name = calendar_name + mock_caldav_principal.calendars.return_value = [mock_calendar] + + result = get_calendar(mock_caldav_principal, calendar_name) + + assert result == mock_calendar + + +def test_get_calendar_not_found(mock_caldav_principal): + """Test getting a calendar that does not exist in the list of calendars.""" + calendar_name = "Nonexistent Calendar" + mock_calendar = MagicMock() + mock_calendar.name = "Different Calendar" + mock_caldav_principal.calendars.return_value = [mock_calendar] + + with pytest.raises(ValueError, match=f"No calendar named '{calendar_name}' found"): + get_calendar(mock_caldav_principal, calendar_name) diff --git a/tests/test_sync_logic.py b/tests/test_sync_logic.py new file mode 100644 index 0000000..498096a --- /dev/null +++ b/tests/test_sync_logic.py @@ -0,0 +1,69 @@ +"""Tests for the sync_logic module.""" + +from datetime import datetime, timezone + +from src.sync_logic import _sanitize_event_for_json, compare_events + + +def test_compare_events_new(sample_event_data): + """Test comparing events with a new event.""" + local_events = {} + server_events = sample_event_data + + new_events, updated_events, deleted_events = compare_events(local_events, server_events) + + assert len(new_events) == 1 + assert len(updated_events) == 0 + assert len(deleted_events) == 0 + assert new_events[0]["uid"] == "test-uid-1" + + +def test_compare_events_updated(sample_event_data): + """Test comparing events with an updated event.""" + local_events = { + "test-uid-1": { + **sample_event_data["test-uid-1"], + "last_modified": "2024-01-01T08:00:00+00:00", # Earlier modification time + }, + } + server_events = sample_event_data + + new_events, updated_events, deleted_events = compare_events(local_events, server_events) + + assert len(new_events) == 0 + assert len(updated_events) == 1 + assert len(deleted_events) == 0 + assert updated_events[0]["uid"] == "test-uid-1" + + +def test_compare_events_deleted(sample_event_data): + """Test comparing events with a deleted event.""" + local_events = sample_event_data + server_events = {} + + new_events, updated_events, deleted_events = compare_events(local_events, server_events) + + assert len(new_events) == 0 + assert len(updated_events) == 0 + assert len(deleted_events) == 1 + assert deleted_events[0]["uid"] == "test-uid-1" + + +def test_sanitize_event_for_json(sample_event_data): + """Test sanitizing an event for JSON serialization.""" + test_datetime = datetime(2024, 12, 31, tzinfo=timezone.utc) + + event = sample_event_data["test-uid-1"].copy() + event["rrule"] = { + "FREQ": "WEEKLY", + "COUNT": 4, + "UNTIL": test_datetime, + "BYDAY": ["MO", "WE", "FR"], + } + + sanitized = _sanitize_event_for_json(event) + + assert sanitized["rrule"]["FREQ"] == "WEEKLY" + assert sanitized["rrule"]["COUNT"] == 4 # noqa PLR2004 + assert isinstance(sanitized["rrule"]["UNTIL"], datetime) + assert sanitized["rrule"]["BYDAY"] == ["MO", "WE", "FR"]