Blog
ENPL

Obsidian + CouchDB livesync — my Notion replacement

Notion was comfortable, but data on someone else's server and a format lock-in. Obsidian + CouchDB livesync gives the same, locally, with markdown on disk. Showing the setup.

·3 min read
Obsidian + CouchDB livesync — my Notion replacement

I had Notion for 3 years. It worked. Until one day I realized exporting my whole base would take two hours and produce HTML chaos. I migrated to Obsidian with CouchDB livesync, markdown on disk, sync across devices, zero external SaaS.

Why Obsidian

Three things:

  1. Files are markdown. I can open them without the app. Grep them. Back them up like any folder.
  2. Locality. Storage is my disk. There's no "cloud sync" by default, I decide if and where to sync.
  3. Plugins. The community is bigger than Notion's was at its peak.

Why CouchDB

Self-hosted livesync needs some database. The obsidian-livesync plugin supports CouchDB and a few others. I picked CouchDB because:

  • it's offline-first (replication)
  • end-to-end encryption (passphrase, plugin encrypts itself)
  • it's stable (since 2005)

Architecture

[iPhone Obsidian] ←→ [Mini PC: CouchDB] ←→ [Macbook Obsidian]

                     [Daily backup: pg_dump-like]

Every device keeps a local vault on disk. The plugin syncs deltas via CouchDB. CouchDB lives on my mini PC, accessible at obsidian-sync.kamilkaletka.dev (Cloudflare tunnel + Zero Trust).

CouchDB setup

Docker compose:

services:
  couchdb:
    image: couchdb:3.3
    environment:
      COUCHDB_USER: admin
      COUCHDB_PASSWORD: ...
    ports:
      - "127.0.0.1:5984:5984"
    volumes:
      - couchdb-data:/opt/couchdb/data
 
volumes:
  couchdb-data:

After docker compose up -d you go to localhost:5984/_utils, create database obsidian-vault, generate a non-admin user, and you're done.

Plugin config

In Obsidian: Settings → Community plugins → Self-hosted LiveSync.

Fields:

  • URI: https://obsidian-sync.kamilkaletka.dev
  • DB name: obsidian-vault
  • Username/Password: non-admin user
  • E2E encryption passphrase: I store mine in 1Password

The passphrase is the KEY thing. Without it the synced data sits plain-text on CouchDB. If someone breaks auth, they read. With the passphrase, encrypted like Fort Knox.

Workflow that works

Daily notes on phone. Siri dictate → Obsidian quick capture → auto-syncs. I get home, open Macbook, continue the note.

Links between notes. [[concept-x]] creates a 2-way link. A graph forms over time which I never got in Notion (with tables and pages).

Tags vs folders. Folders for "when" (year-month), tags for "what about". A tag can sit on 50 notes, a folder usually holds 1.

Pitfalls

1. Lost passphrase = lost vault. Plain text on CouchDB is encrypted. If you lose the passphrase, you can't decrypt. Back up the passphrase in a safe place.

2. Merge conflicts. Two devices edit the same note offline → on sync the plugin creates note.conflict.md. Manual merge. Rare, but painful.

3. Migration from Notion. Notion's export is chaos. I used notion-to-obsidian as a start, then 3 days of manual cleanup. Worth checking pre-migration whether anything is Notion-only formatted.

4. Mobile sync latency. The plugin replicates every ~30 seconds by default. If you want ASAP, set replication interval to 5s in the plugin.

What I lost (and don't miss)

  • Tables with formulas. Notion had inline DBs. Obsidian has the Dataview plugin, but it's not the same. Loss acceptable for me.
  • Real-time collaboration. Notion had Google Docs-style. CouchDB livesync is async. If you collaborate with 5 people, Obsidian isn't that tool.
  • UI templates. Notion had a pretty template UI. Obsidian has a plugin, uglier but functional.

After a year on Obsidian + CouchDB I'm not going back. Markdown on disk is peace of mind that cloud can't give. And livesync solves the only real downside of self-hosting, multi-device. Setup takes an hour, payoff shows in a week.