import { apiFetch, type ApiSettings } from "@govoplan/core-webui"; export type CalendarCollection = { id: string; tenant_id: string; slug: string; name: string; description?: string | null; timezone: string; color?: string | null; owner_type: string; owner_id?: string | null; visibility: string; is_default: boolean; created_at: string; updated_at: string; metadata?: Record | null; }; export type CalendarEvent = { id: string; tenant_id: string; calendar_id: string; uid: string; recurrence_id?: string | null; sequence: number; summary: string; description?: string | null; location?: string | null; status: string; transparency: string; classification: string; start_at: string; end_at?: string | null; duration_seconds?: number | null; all_day: boolean; timezone?: string | null; organizer?: Record | null; attendees: Record[]; categories: string[]; rrule?: Record | null; rdate: Record[]; exdate: Record[]; reminders: Record[]; attachments: Record[]; related_to: Record[]; source_kind: string; source_href?: string | null; etag?: string | null; icalendar: Record; created_at: string; updated_at: string; metadata?: Record | null; }; export type CalendarCollectionListResponse = { calendars: CalendarCollection[] }; export type CalendarEventListResponse = { events: CalendarEvent[] }; export type CalendarDeltaDeletedItem = { id: string; resource_type?: string | null; revision?: string | null; deleted_at?: string | null }; export type CalendarEventDeltaResponse = { events: CalendarEvent[]; deleted: CalendarDeltaDeletedItem[]; watermark?: string | null; has_more: boolean; full: boolean; }; export type CalendarCalDavAuthType = "none" | "basic" | "bearer"; export type CalendarCalDavSyncDirection = "inbound" | "two_way"; export type CalendarCalDavConflictPolicy = "etag" | "overwrite"; export type CalendarSyncSourceKind = "caldav" | "ics" | "webcal" | "graph" | "ews"; export type CalendarSyncSource = { id: string; tenant_id: string; calendar_id: string; source_kind: CalendarSyncSourceKind; collection_url: string; display_name?: string | null; auth_type: CalendarCalDavAuthType; username?: string | null; credential_ref?: string | null; has_credential: boolean; sync_enabled: boolean; sync_interval_seconds: number; sync_direction: CalendarCalDavSyncDirection; conflict_policy: CalendarCalDavConflictPolicy; sync_token?: string | null; ctag?: string | null; last_attempt_at?: string | null; last_synced_at?: string | null; next_sync_at?: string | null; last_status?: string | null; last_error?: string | null; created_at: string; updated_at: string; metadata?: Record | null; }; export type CalendarCalDavSource = CalendarSyncSource; export type CalendarSyncSourceListResponse = { sources: CalendarSyncSource[] }; export type CalendarCalDavSourceListResponse = { sources: CalendarCalDavSource[] }; export type CalendarCalDavDiscoveryCandidate = { collection_url: string; href: string; display_name?: string | null; color?: string | null; ctag?: string | null; sync_token?: string | null; }; export type CalendarCalDavDiscoveryPayload = { url: string; source_id?: string | null; auth_type?: CalendarCalDavAuthType | null; username?: string | null; credential_ref?: string | null; password?: string | null; bearer_token?: string | null; }; export type CalendarCalDavDiscoveryResponse = { calendars: CalendarCalDavDiscoveryCandidate[] }; export type CalendarSyncSourceCreatePayload = { source_kind?: CalendarSyncSourceKind; calendar_id: string; collection_url: string; display_name?: string | null; auth_type?: CalendarCalDavAuthType; username?: string | null; credential_ref?: string | null; password?: string | null; bearer_token?: string | null; sync_enabled?: boolean; sync_interval_seconds?: number; sync_direction?: CalendarCalDavSyncDirection; conflict_policy?: CalendarCalDavConflictPolicy; metadata?: Record; }; export type CalendarCalDavSourceCreatePayload = CalendarSyncSourceCreatePayload; export type CalendarCalDavSourceUpdatePayload = Partial; export type CalendarSyncSourceUpdatePayload = Partial; export type CalendarSyncSourceSyncPayload = { password?: string | null; bearer_token?: string | null; force_full?: boolean; }; export type CalendarCalDavSyncPayload = CalendarSyncSourceSyncPayload; export type CalendarSyncSourceSyncResponse = { source: CalendarSyncSource; created: number; updated: number; deleted: number; unchanged: number; fetched: number; full_sync: boolean; used_sync_token: boolean; sync_token?: string | null; ctag?: string | null; errors: string[]; }; export type CalendarCalDavSyncResponse = CalendarSyncSourceSyncResponse; export type CalendarCollectionCreatePayload = { name: string; slug?: string | null; description?: string | null; timezone?: string; color?: string | null; owner_type?: "tenant" | "user" | "group" | "resource"; owner_id?: string | null; visibility?: "private" | "tenant" | "shared" | "public"; is_default?: boolean; metadata?: Record; }; export type CalendarCollectionUpdatePayload = Partial; export type CalendarDeleteEventAction = "delete" | "move"; export type CalendarCollectionDeletePayload = { event_action?: CalendarDeleteEventAction; target_calendar_id?: string | null; make_target_default?: boolean; }; export type CalendarEventCreatePayload = { calendar_id?: string | null; uid?: string | null; recurrence_id?: string | null; sequence?: number; summary: string; description?: string | null; location?: string | null; status?: string; transparency?: string; classification?: string; start_at: string; end_at?: string | null; duration_seconds?: number | null; all_day?: boolean; timezone?: string | null; organizer?: Record | null; attendees?: Record[]; categories?: string[]; rrule?: Record | null; rdate?: Record[]; exdate?: Record[]; reminders?: Record[]; attachments?: Record[]; related_to?: Record[]; source_kind?: string; source_href?: string | null; etag?: string | null; icalendar?: Record; metadata?: Record; }; export type CalendarEventUpdatePayload = Partial; export function listCalendars(settings: ApiSettings): Promise { return apiFetch(settings, "/api/v1/calendar/calendars"); } export function createCalendar(settings: ApiSettings, payload: CalendarCollectionCreatePayload): Promise { return apiFetch(settings, "/api/v1/calendar/calendars", { method: "POST", body: JSON.stringify(payload) }); } export function updateCalendar(settings: ApiSettings, calendarId: string, payload: CalendarCollectionUpdatePayload): Promise { return apiFetch(settings, `/api/v1/calendar/calendars/${calendarId}`, { method: "PATCH", body: JSON.stringify(payload) }); } export function deleteCalendar(settings: ApiSettings, calendarId: string, payload: CalendarCollectionDeletePayload = { event_action: "delete" }): Promise { return apiFetch(settings, `/api/v1/calendar/calendars/${calendarId}`, { method: "DELETE", body: JSON.stringify(payload) }); } export function listSyncSources(settings: ApiSettings, params: { calendar_id?: string; source_kind?: CalendarSyncSourceKind } = {}): Promise { const search = new URLSearchParams(); if (params.calendar_id) search.set("calendar_id", params.calendar_id); if (params.source_kind) search.set("source_kind", params.source_kind); const suffix = search.toString() ? `?${search.toString()}` : ""; return apiFetch(settings, `/api/v1/calendar/sync-sources${suffix}`); } export function listCalDavSources(settings: ApiSettings, params: { calendar_id?: string } = {}): Promise { const search = new URLSearchParams(); if (params.calendar_id) search.set("calendar_id", params.calendar_id); const suffix = search.toString() ? `?${search.toString()}` : ""; return apiFetch(settings, `/api/v1/calendar/caldav/sources${suffix}`); } export function discoverCalDavCalendars(settings: ApiSettings, payload: CalendarCalDavDiscoveryPayload): Promise { return apiFetch(settings, "/api/v1/calendar/caldav/discover", { method: "POST", body: JSON.stringify(payload) }); } export function createSyncSource(settings: ApiSettings, payload: CalendarSyncSourceCreatePayload): Promise { return apiFetch(settings, "/api/v1/calendar/sync-sources", { method: "POST", body: JSON.stringify(payload) }); } export function createCalDavSource(settings: ApiSettings, payload: CalendarCalDavSourceCreatePayload): Promise { return apiFetch(settings, "/api/v1/calendar/caldav/sources", { method: "POST", body: JSON.stringify(payload) }); } export function updateSyncSource(settings: ApiSettings, sourceId: string, payload: CalendarSyncSourceUpdatePayload): Promise { return apiFetch(settings, `/api/v1/calendar/sync-sources/${sourceId}`, { method: "PATCH", body: JSON.stringify(payload) }); } export function updateCalDavSource(settings: ApiSettings, sourceId: string, payload: CalendarCalDavSourceUpdatePayload): Promise { return apiFetch(settings, `/api/v1/calendar/caldav/sources/${sourceId}`, { method: "PATCH", body: JSON.stringify(payload) }); } export function deleteSyncSource(settings: ApiSettings, sourceId: string): Promise { return apiFetch(settings, `/api/v1/calendar/sync-sources/${sourceId}`, { method: "DELETE" }); } export function deleteCalDavSource(settings: ApiSettings, sourceId: string): Promise { return apiFetch(settings, `/api/v1/calendar/caldav/sources/${sourceId}`, { method: "DELETE" }); } export function syncSyncSource(settings: ApiSettings, sourceId: string, payload: CalendarSyncSourceSyncPayload = {}): Promise { return apiFetch(settings, `/api/v1/calendar/sync-sources/${sourceId}/sync`, { method: "POST", body: JSON.stringify(payload) }); } export function syncCalDavSource(settings: ApiSettings, sourceId: string, payload: CalendarCalDavSyncPayload = {}): Promise { return apiFetch(settings, `/api/v1/calendar/caldav/sources/${sourceId}/sync`, { method: "POST", body: JSON.stringify(payload) }); } export function listCalendarEvents( settings: ApiSettings, params: { calendar_id?: string; start_at?: string; end_at?: string } = {} ): Promise { const search = new URLSearchParams(); if (params.calendar_id) search.set("calendar_id", params.calendar_id); if (params.start_at) search.set("start_at", params.start_at); if (params.end_at) search.set("end_at", params.end_at); const suffix = search.toString() ? `?${search.toString()}` : ""; return apiFetch(settings, `/api/v1/calendar/events${suffix}`); } export function listCalendarEventsDelta( settings: ApiSettings, params: { calendar_id?: string; start_at?: string; end_at?: string; since?: string | null; limit?: number } = {} ): Promise { const search = new URLSearchParams(); if (params.calendar_id) search.set("calendar_id", params.calendar_id); if (params.start_at) search.set("start_at", params.start_at); if (params.end_at) search.set("end_at", params.end_at); if (params.since) search.set("since", params.since); if (params.limit) search.set("limit", String(params.limit)); const suffix = search.toString() ? `?${search.toString()}` : ""; return apiFetch(settings, `/api/v1/calendar/events/delta${suffix}`); } export function createCalendarEvent(settings: ApiSettings, payload: CalendarEventCreatePayload): Promise { return apiFetch(settings, "/api/v1/calendar/events", { method: "POST", body: JSON.stringify(payload) }); } export function updateCalendarEvent(settings: ApiSettings, eventId: string, payload: CalendarEventUpdatePayload): Promise { return apiFetch(settings, `/api/v1/calendar/events/${eventId}`, { method: "PATCH", body: JSON.stringify(payload) }); } export function deleteCalendarEvent(settings: ApiSettings, eventId: string): Promise { return apiFetch(settings, `/api/v1/calendar/events/${eventId}`, { method: "DELETE" }); }