# room-cal A self-hosted calendar management tool for short-term rental hosts. It syncs pricing, availability, reservations, and discounts between a local CalDAV calendar and external booking platforms (Airbnb, Booking.com). A FastAPI HTTP server exposes the data to a Vue-based web calendar, and a FastMCP server exposes health checks to AI assistants. --- ## Installation See [docker/README.md](docker/README.md) for container-based deployment (recommended for production). For local development: ```bash # Install dependencies (requires uv) uv sync --group dev # Activate git hooks git config core.hooksPath .githooks ``` --- ## Configuration Start from `room_cal/config.json` (the bundled defaults) and place an override at `~/.local/room_cal/config.json` (or `$ROOM_CAL_DATA_HOME/config.json`). Keys are deep-merged — you only need to include what you want to change. `room_cal/config-all.json` is a generated file that shows every available config key with its default value. It is kept up to date automatically by the pre-commit hook and is the canonical reference for what can be configured. --- ## Usage ### CLI ```bash # Sync reservations, prices, and availability for a date range uv run room-cal fetch-reservations 2026-07-01 2026-07-31 uv run room-cal fetch-prices 2026-07-01 2026-07-31 uv run room-cal push-prices 2026-07-01 2026-07-31 uv run room-cal fetch-closed 2026-07-01 2026-07-31 uv run room-cal push-closed 2026-07-01 2026-07-31 # Apply discount rules and show a diff uv run room-cal apply-rules 2026-07-01 2026-07-31 uv run room-cal apply-discounts 2026-07-01 2026-07-31 uv run room-cal diff 2026-07-01 2026-07-31 # Create default prices for dates with no local price set uv run room-cal fill-prices 2026-07-01 2026-07-31 [--weekday 150] [--weekend 200] # Fetch an external iCal feed uv run room-cal fetch-feed 2026-07-01 2026-07-31 --feed-name Fire # Sync from user calendar; push busy export calendar uv run room-cal fetch-user-cal 2026-07-01 2026-07-31 uv run room-cal push-busy 2026-07-01 2026-07-31 # Local-only workflows (no service API calls) uv run room-cal local-sync 2026-07-01 2026-07-31 # feeds + rules + fill + busy uv run room-cal local-refresh 2026-07-01 2026-07-31 # rewrite all local Room calendar events ``` ### API server ```bash uv run room-api ``` Serves the web calendar at `http://localhost:8000` and exposes REST endpoints for all sync operations. --- ## Refreshing credentials (`refresh-creds`) Session cookies for Airbnb and Booking.com are obtained via a Playwright browser session and must be periodically refreshed. ```bash uv run refresh-creds [--output=file|stdout|api] ``` Three output modes are available: | Mode | Behaviour | |------|-----------| | `file` (default) | Writes credentials to `airbnb.env` and `booking.env` in `$ROOM_CAL_DATA_HOME` | | `stdout` | Prints credentials to stdout — useful for piping or inspection | | `api` | POSTs credentials directly to a running room-api instance | The `api` mode requires `api_url` to be set in your `config.json`: ```json { "api_url": "https://your-room-cal-instance.example.com" } ``` --- ## Web calendar (`calendar.html`) The web calendar provides a month view of all pricing and availability data. Key features: - **Month navigation** — prev/next buttons to move between months - **Day detail panel** — click any day to see its price, discount, reservation, and closed status for each service; prices and discounts are editable inline - **Sync mode** — toggle the sync bar on to see which days have mismatches between local CalDAV and remote platforms; a badge shows the total number of days with issues - **Per-day sync controls** — push (↑) or fetch (↓) prices, closed status, discounts, reservations, and user calendar data for individual days - **Per-month sync controls** — bulk push or fetch prices and closed status for the entire visible month; a Fill button creates default local prices for any missing dates - **iCal feed blocks** — external feed closures (e.g. a fire safety calendar) are shown and can be fetched per day - **Rule discounts** — pipeline-generated discounts are shown alongside manual discounts; mismatches between the rule output and what's on the calendar are surfaced - **Health indicator** — a header button polls `GET /health` and shows green/amber/red based on CalDAV connectivity and service credential status --- ## Developer notes ### Git hooks The repo includes a pre-commit hook that regenerates `room_cal/config-all.json` automatically on every commit. After cloning, activate it with: ```bash git config core.hooksPath .githooks ``` To regenerate the file manually: ```bash uv run python scripts/gen_example_config.py > room_cal/config-all.json ``` ### Tests Store tests run without any live server. Service API and CalDAV tests require live credentials: ```bash uv run python -m pytest tests/ ```