End-to-end guide to deploy your own Excalidraw stack — editor, real-time collaboration, and scene storage — on Clever Cloud.
Two deployment paths covered in parallel: clever CLI for hands-on learning, and Terraform for reproducibility.
flowchart LR
user(["🧑 Browser"])
subgraph CC["Clever Cloud"]
front["Frontend<br/>Vite static<br/>draw.example.com"]
room["excalidraw-room<br/>Socket.IO<br/>Node.js"]
storage["storage-backend<br/>Express<br/>Node.js"]
cellar[("Cellar<br/>S3 add-on")]
end
user -- HTTPS --> front
front -- WebSocket --> room
front -- POST/GET scenes --> storage
storage -- S3 API --> cellar
Three Clever Cloud apps + one add-on:
| Component | Source | CC runtime | Add-ons |
|---|---|---|---|
| frontend | fork of excalidraw/excalidraw |
static | — |
| room | fork of excalidraw/excalidraw-room |
Node.js | — |
| storage | written here | Node.js | Cellar |
clever_projects/excalidraw/
├── README.md
├── docs/
│ ├── tutorials/ ← step-by-step procedures (read in order)
│ └── notions/ ← conceptual explanations (read as needed)
├── frontend/ ← clone of your fork (or symlink)
├── room/ ← clone of your fork (or symlink)
├── storage/ ← we build this
└── terraform/ ← reproducible infra
- 00 — Prerequisites — tools + accounts
- 01 — Fork & clone — repo strategy + upstream tracking
- 02 — Storage backend — custom Node + Cellar
- 03 — Collaboration room — Socket.IO server
- 04 — Frontend — build + static deploy
- 05 — Terraform — reproduce everything in HCL
- 99 — Updates & troubleshooting — pull upstream, verify
Conceptual background for the decisions in the tutorials. Read as needed — each tutorial links to the relevant notion at the top.
- Storage backend — why a self-hosted Excalidraw scene store fits in 50 lines (E2E encryption, URL fragment as secret channel, blob-only API)
- Collaboration protocol — how
excalidraw-roomrelays encrypted events without seeing content, room ID vs key, Socket.IO volatile vs durable channels - Frontend build & env vars — Vite's build-time env substitution, why deploy = rebuild, why we pick static-apache over Node
- Terraform on Clever Cloud — provider auth model, infra-vs-code split,
dependenciessemantics, using Cellar as TF state backend
Excalidraw encrypts scenes end-to-end client-side. Your storage backend never sees plaintext — it just stores opaque blobs. That's why our custom backend in tutorial 02 is only ~50 lines of code: it's a thin proxy in front of Cellar (S3). No application logic, no schema, no DB. Full reasoning in docs/notions/storage-backend.md.