Calendar Events & ICS Feeds
Relevant source files
The following files were used as context for generating this wiki page:
The Calendar Events & ICS Feeds system provides a centralized interface for tracking compliance-related deadlines, renewals, and automated scan schedules. It utilizes a one-way calendar linking mechanism (RFC 5545) that allows users to project project-specific events into external calendar applications like Google Calendar, Microsoft Outlook, and Apple Calendar.
This module is primarily designed to ensure that developers and merchants stay informed about critical compliance milestones, such as CCPA/GDPR enforcement updates or subscription renewals, without needing to manually check the dashboard. The system handles pure date-only "all-day" events, reflecting the nature of compliance deadlines.
Sources: src/lib/calendar/ics.ts:1-10, src/app/dashboard/calendar/CalendarView.tsx:160-170
Data Models and Schemas
The system relies on a specific event structure and a database schema for managing subscription tokens.
Calendar Event Structure
Compliance events are categorized by type and severity to provide clear visual cues and prioritization in both the dashboard and external feeds.
| Field | Type | Description |
|---|---|---|
id | string | Stable unique identifier (UUID or synthetic). |
date | string | ISO YYYY-MM-DD UTC date. |
category | CalendarCategory | task, renewal, scan, risk, or regulation. |
severity | CalendarSeverity | info, warning, or critical. |
status | CalendarStatus | pending, done, or dismissed. |
editable | boolean | Whether the event can be modified manually. |
Sources: src/lib/calendar/events.ts:11-28
Database Schema: calendar_feeds
The calendar_feeds table manages the capability-based security tokens used to access the ICS endpoint.
The diagram shows the relationship between users and their unique calendar feed tokens.
Sources: supabase/migrations/0014_calendar_feeds.sql:17-25
ICS Feed Generation (RFC 5545)
The ics.ts module serves as a pure, testable serializer that transforms CalendarEvent objects into an iCalendar document.
Serialization Logic
The system generates all-day events by setting the DTSTART to the event date and DTEND to the subsequent day. Textual fields are escaped per RFC 5545 §3.3.11 to handle backslashes, commas, and newlines correctly.
- Priority Mapping: Compliance
severityis mapped to iCalendarPRIORITYvalues (1 for critical, 5 for warning, 9 for info). - UID Stability: UIDs are generated using the event ID and a
@comply-quicksuffix to ensure that re-subscribing updates existing events rather than duplicating them. - Line Folding: Long content lines are folded to 75 octets with CRLF and space continuation to ensure compatibility with major calendar providers.
Sources: src/lib/calendar/ics.ts:17-43, src/lib/calendar/ics.ts:60-84, src/tests/calendar-ics.test.ts:47-65
ICS Feed Attributes
The generated VCALENDAR includes several X-headers and properties to control client behavior:
| Property | Value / Description |
|---|---|
PRODID | -//Comply-Quick//Compliance Calendar//EN |
X-WR-CALNAME | Configurable display name (Default: "Comply-Quick Compliance") |
REFRESH-INTERVAL | PT12H (Suggests a 12-hour sync frequency) |
METHOD | PUBLISH |
Sources: src/lib/calendar/ics.ts:100-115
UI and Subscription Flow
The CalendarView component provides the interface for both managing tasks and configuring the external feed.
The flowchart illustrates the process from a user requesting a link to the final external calendar subscription.
Sources: src/app/dashboard/calendar/CalendarView.tsx:170-220
Feed URLs and Redirection
The system generates specific URLs for different platforms:
- Webcal:
webcal://<origin>/api/calendar/feed/<token>.ics - Google Calendar: A direct link using the
cidparameter pointing to the webcal URL. - Outlook: A direct link using the
urlparameter.
Sources: src/app/dashboard/calendar/CalendarView.tsx:88-95
Calendar Math and Logic
The events.ts module provides utility functions for grid calculation and scan scheduling.
- Month Range Calculation: The
monthRangefunction calculates the boundaries for a 6-week (42-cell) grid, ensuring it always starts on a Sunday and ends on a Saturday, padding the month as necessary. - Scan Projections:
nextScanDuecalculates the next compliance scan date by addingSCAN_INTERVAL_DAYS(default 7) to thelastScannedAtdate or falling back to thecreatedAtdate. - Event Bucketing:
bucketByDaygroups events into aMap<string, CalendarEvent[]>keyed byYYYY-MM-DD, sorted by severity within each day.
Sources: src/lib/calendar/events.ts:61-84, src/lib/calendar/events.ts:91-94, src/lib/calendar/events.ts:104-118
Security and Revocation
The ICS endpoint is public but protected by unguessable tokens. Security is managed through:
- Capability-based Security: The token itself acts as the authorization; no anonymous SELECT policy is granted on the
calendar_feedstable. - Rotation: Users can rotate their feed URL via
POST /api/calendar/feed, which revokes the old token (settingrevoked_at) and issues a new one. - Strict One-Way Flow: The system only projects events outwards; it does not read any data back from the user's external calendar.
Sources: supabase/migrations/0014_calendar_feeds.sql:35-43, src/app/dashboard/calendar/CalendarView.tsx:109-124