
Fredy Acuna / June 19, 2025 / 5 min read
The LiveSync plugin for Obsidian is one of the best self-hosted services I've set up. It provides seamless, instant, and secure note synchronization across all devices. Since most tutorials skip essential details, I created this comprehensive guide using Docker, CouchDB, and Traefik.
If you've ever bounced between tools like Notion, Microsoft Loop, or even Apple Notes, you probably know the frustration: great features, but limited control. Maybe you’ve tried Obsidian and loved its local-first approach — but hit a wall when it came to syncing your notes across devices without paying or giving up control.
This guide is for people who want:
We’ll walk you through every step — no assumptions, no skipped details. By the end, you'll have a fully functional sync setup using Docker, CouchDB, Traefik, and the Obsidian LiveSync plugin.
Let’s build your own personal sync server — no subscriptions, no black boxes.
This setup includes:
your-domain.com) and a subdomain pointing to your server (e.g., obsidian.your-domain.com).Depending on how your server is configured, this step may look slightly different for you.
💡 Note: This tutorial assumes you're using Docker with Traefik as a reverse proxy. If you're using another reverse proxy (like Nginx or Caddy), or deploying to a platform like CapRover or Dokku, adapt this step accordingly — the core idea is the same: expose CouchDB securely over HTTPS.
services:
couchdb-obsidian-livesync:
container_name: obsidian-livesync
image: couchdb:3.3.3
restart: unless-stopped
environment:
- PUID=1000
- PGID=1000
- TZ=America/Bogota
- COUCHDB_USER=obsidian_user
- COUCHDB_PASSWORD=YOUR_VERY_STRONG_PASSWORD
volumes:
- ./data:/opt/couchdb/data
- ./etc/local.d:/opt/couchdb/etc/local.d
networks:
- traefik-net
labels:
- "traefik.enable=true"
- "traefik.http.routers.obsidian.rule=Host(`obsidian.your-domain.com`)"
- "traefik.http.routers.obsidian.entrypoints=https"
- "traefik.http.routers.obsidian.tls.certresolver=letsencrypt"
- "traefik.http.services.obsidian.loadbalancer.server.port=5984"
networks:
traefik-net:
external: true
Note: 🔐 Make sure to replace passwords and domain names. 📂 Persist your volumes to avoid losing data on container restart.
Then run:
docker-compose up -d
If you're not using Traefik, here’s what to focus on:
Navigate to:
https://obsidian.your-domain.com/_utils/
COUCHDB_USER and COUCHDB_PASSWORD defined in your docker-compose.yml.<-> icon in the top-left to expand the sidebar.obsidiandb (or unique names like obsidiandb_fredy)Non-partitioned.Head to Configuration in the sidebar.
Click + Add Option and enter the following settings:
| Section | Name | Value |
|---|---|---|
| chttpd | require_valid_user | true |
| chttpd_auth | require_valid_user | true |
| httpd | WWW-Authenticate | Basic realm="couchdb" |
| httpd | enable_cors | true |
| chttpd | enable_cors | true |
| chttpd | max_http_request_size | 4294967296 |
| couchdb | max_document_size | 50000000 |
| cors | credentials | true |
| cors | origins | app://obsidian.md, capacitor://localhost, http://localhost |
Click Save Changes after each addition.
Remote Type: CouchDB
URI: https://obsidian.your-domain.com
Username: obsidian_user
Password: YOUR_VERY_STRONG_PASSWORD
Database Name: obsidiandb