$ show lennart-k/rustical
Rustical is an open-source CalDAV and CardDAV server written in Rust, providing a lightweight, self-hosted alternative for calendar and addressbook synchronization. It implements the core WebDAV extensions (RFC 4791, 6352) with support for CalDAV scheduling, CardDAV group membership, WebDAV Push (web-push) notifications, and a built-in web frontend for management. The architecture is a modular Rust workspace with separate crates for DAV infrastructure, protocol handlers (caldav, carddav), storage abstraction, SQLite backend, XML serialization, OIDC authentication, and a Lit-based web UI. The server exposes RESTful HTTP endpoints via Axum, uses SQLite for persistence with `sqlx`, and supports app tokens, OIDC, and Nextcloud login for authentication. The codebase demonstrates solid engineering with thorough integration tests, snapshot testing, CI/CD pipelines, and a clear separation of concerns. However, it contains some workarounds and TODOs indicating active development rather than a polished final product. The custom XML derive macros and store trait pattern are particularly well-crafted and potentially reusable.
The LLM identified 4 files worth highlighting for reuse:
This procedural macro crate provides `#[derive(XmlDeserialize, XmlSerialize)]` for automatically generating XML serialization/deserialization code for Rust structs and enums. It supports attributes for namespace, renaming, and type mapping, reducing boilerplate in WebDAV XML handling. The implementation is non-obvious, handling untagged variants, nested namespaces, and custom type conversions. It is a high-craftsmanship component that could be extracted for any XML-heavy Rust project requiring a serde-like experience.
The `rustical_store` crate defines the core storage traits (`CalendarReadStore`, `CalendarWriteStore`, `AddressbookReadStore`, `AddressbookWriteStore`, `AuthenticationProvider`) that decouple protocol logic from backend implementation. This pattern enables swapping SQLite for other databases (e.g., PostgreSQL) without modifying the DAV handlers. The traits are async, use associated types for errors, and follow a resource-oriented design. This is a clean, reusable abstraction for any service needing pluggable persistence.
The `Resource` trait and `ResourceService` struct provide a generic framework for handling WebDAV operations (PROPFIND, PROPPATCH, DELETE, MOVE, COPY) on hierarchical resources. It encapsulates common logic like depth handling, locking, and XML multistatus responses, and allows concrete implementations for calendars and addressbooks. This pattern simplifies adding new resource types and demonstrates a clean separation of protocol concerns.
The `SqliteCalendarStore` implements the calendar storage traits with a well-designed schema tracking changes via `calendarobjectchangelog` table and monotonically increasing sync tokens. It supports pagination, soft-delete (trashbin), pruning of old data, and repair operations. The implementation uses transactional `BEGIN IMMEDIATE` to avoid write conflicts and includes a `skip_broken` flag for graceful malformed object handling. This is a robust, reusable persistence layer for any sync-oriented application.