• v0.12.0 048459c878

    v0.12.0 — the calendar moves to its own hostname
    All checks were successful
    CI / gate (push) Successful in 1m16s
    CI / image (push) Successful in 51s
    Stable

    joeyr released this 2026-08-12 08:45:02 -05:00 | 62 commits to main since this release

    The calendar moves off the apex and onto its own hostname,
    https://icloudcalendar.mcp.jrendar.org/icloudcalendar. Nothing about what it does
    changes; where it lives does.

    Breaking, and it cannot be made otherwise. PUBLIC_BASE_URL is both the token issuer
    and the token audience, so moving it kills every token this connector has ever been
    issued. They are dead rather than refreshable: remove and re-add the connector in
    Claude
    , and its permission toggles reset with it. The Forgejo OAuth application's
    redirect URI has to be repointed at the new callback before the deploy or sign-in fails
    looking like an auth bug.

    This shipped alone, on purpose. The whole failure mode is an auth error that presents as a
    bug in whatever else went out at the same time.

    Changed

    • The hostname and the path. mcp.jrendar.org/calendar
      icloudcalendar.mcp.jrendar.org/icloudcalendar. Calendar was the last thing not
      following the rule probe 0 settled on 2026-08-11 — a tenant is a hostname — because it
      was built when the README still claimed a tenant was another path on one host. Nothing
      serves the apex now
      ; a proxy host left behind there points at a name that no longer
      resolves and answers 502 on a URL that still looks live.

    • One name end to end. The tenant was already icloudcalendar while its path was
      /calendar and its Swarm alias was calendar. Both now match the tenant, the way mail's
      have from the start: service icloudcalendar, alias icloudcalendar, MCP_PATH
      /icloudcalendar, upstream http://icloudcalendar:8787. The default mcp_path in
      config.py moved with them — deployments set it explicitly, so the default only decides
      what a local run without an .env does.

    • deploy/nginx/calendar.confdeploy/nginx/icloudcalendar.conf, which also settles
      the filename convention as <tenant>.conf rather than the <hostname>.conf three
      documents claimed. The hostname is <tenant>.mcp.jrendar.org, so the repeated suffix
      bought nothing. Both nginx files change together, as their headers require.

    • pyproject.toml's description no longer says tenant #1 is read-only. It has not been
      since 0.5.0, and there have been two tenants since M1.

    Notes

    • The procedure is now in docs/operations.md under Moving a tenant to a new
      hostname
      , in the order that matters: redirect URI, proxy host, stack repaste, delete the
      old proxy host, re-add the connector. ALLOWED_HOSTS is the step that fails loudest if
      forgotten — every request is refused before it reaches a tool.

    • The failure table gained the cached-upstream 502, which cost a live calendar outage
      on 2026-08-11 and had been fixed in the configs without ever being written down as a
      symptom. It is the 502 to expect on the new host during this move, and the one whose
      obvious suspect — the app — is innocent.

    • docs/icloud-calendar-plan.md is gone, emptied by this release as its own header
      said it would be. What is left to build lives in docs/icloud-mail-plan.md (M2–M4).

    Downloads