Deep dives on software engineering, architecture, and the real-world decisions
This blog runs on software I wrote. Here's everything I learned doing it.
Latest posts
// Make sure it won't end up in production!!!
const TODO = "remove before production";Building a CardDAV Server for Customer Contacts - When Next.js Gets in the Way
May 12, 2026One of the features I wanted to add to timeli.sh is the ability for service businesses to sync their customer list directly to their phone's contacts app. If a client calls, the business owner should see "Sarah - Haircut Tuesday 3pm" rather than an unknown number. The standard protocol for this is CardDAV - the same protocol Apple Contacts, Google Contacts, and most third-party apps use to sync address books.
The implementation ended up being two distinct pieces: a connected app in the app store that organizations install and configure, and a separate lightweight Node.js server that actually speaks CardDAV. The reason those are separate - and why the CardDAV server is not just a Next.js API route - comes down to one hard limitation in Next.js that I hit immediately.
Why Next.js can't host a CardDAV server
Next.js App Router Route Handlers support a fixed set of HTTP methods: GET, POST, PUT, PATCH, DELETE, HEAD, and OPTIONS. You export a function named after the method and Next.js routes requests to it.