%%%------------------------------------------------------------------- %%% @doc Тесты клиентского API для событий. %%% Покрывает POST /v1/calendars/:id/events и GET /v1/events/:id/occurrences %%% @end %%%------------------------------------------------------------------- -module(user_events_tests). -include_lib("eunit/include/eunit.hrl"). -export([test/0]). -spec test() -> ok. test() -> ct:pal("=== User Events Tests ==="), Token = api_test_runner:get_user_token(), % Создаём календарь CalId = api_test_runner:create_calendar(Token, #{title => <<"EventsTest">>}), % Тесты test_create_single_event(Token, CalId), test_list_events_with_dates(Token, CalId), test_create_recurring_event(Token, CalId), ct:pal("=== All user events tests passed ==="), ok. %% @doc POST /v1/calendars/:calendar_id/events – одиночное событие. test_create_single_event(Token, CalId) -> ct:pal(" TEST: Create single event"), Path = <<"/v1/calendars/", CalId/binary, "/events">>, Body = jsx:encode(#{ title => <<"Single Event">>, start_time => <<"2026-06-01T10:00:00Z">>, duration => 60 }), Resp = api_test_runner:client_request(post, Path, Token, Body), {ok, 201, _, RespBody} = Resp, #{<<"id">> := EventId, <<"title">> := Title} = jsx:decode(list_to_binary(RespBody), [return_maps]), ?assert(is_binary(EventId)), ?assertEqual(<<"Single Event">>, Title), ct:pal(" OK: created event ~s", [EventId]). %% @doc GET /v1/calendars/:calendar_id/events?from=...&to=... – список с фильтром. test_list_events_with_dates(Token, CalId) -> ct:pal(" TEST: List events with date range"), Path = <<"/v1/calendars/", CalId/binary, "/events?from=2026-05-01T00:00:00Z&to=2026-07-01T00:00:00Z">>, Events = api_test_runner:client_get(Path, Token), ?assert(is_list(Events)), ?assert(length(Events) >= 1), First = hd(Events), ?assert(maps:is_key(<<"id">>, First)), ?assert(maps:is_key(<<"title">>, First)), ct:pal(" OK: ~p events found", [length(Events)]). %% @doc POST /v1/calendars/:calendar_id/events – повторяющееся событие и проверка вхождений. test_create_recurring_event(Token, CalId) -> ct:pal(" TEST: Create recurring event and check occurrences"), Path = <<"/v1/calendars/", CalId/binary, "/events">>, Body = jsx:encode(#{ title => <<"Weekly Meeting">>, start_time => <<"2026-06-01T10:00:00Z">>, duration => 60, recurrence => #{ freq => <<"WEEKLY">>, interval => 1 } }), Resp = api_test_runner:client_request(post, Path, Token, Body), {ok, 201, _, RespBody} = Resp, #{<<"id">> := RecurringId} = jsx:decode(list_to_binary(RespBody), [return_maps]), ct:pal(" Created recurring event ~s", [RecurringId]), % Запрашиваем вхождения на месяц OccPath = <<"/v1/events/", RecurringId/binary, "/occurrences?from=2026-06-01T00:00:00Z&to=2026-06-30T00:00:00Z">>, Occs = api_test_runner:client_get(OccPath, Token), ?assert(is_list(Occs)), ?assert(length(Occs) >= 4), % минимум 4 недели в июне FirstOcc = hd(Occs), ?assert(maps:is_key(<<"start_time">>, FirstOcc)), ct:pal(" OK: ~p occurrences found", [length(Occs)]).