Our Collaborative Editor lesson weighs Operational Transform against CRDTs for shared editing. Figma — a design tool where many people drag, resize, and restyle objects on the same canvas in real time — made a pragmatic choice that is worth studying, because it shows how the shape of the data decides the consistency strategy.
The problem
A Figma file is not a stream of text; it is a tree of objects — frames, shapes, text nodes — each with properties like position, size, color, and parent. Many editors operate on it at once, and every change must appear on everyone’s screen within tens of milliseconds, or the collaboration feels broken. Edits also keep flowing while someone is briefly offline, and must reconcile when they reconnect.
One server owns each document
Figma’s central decision is to give each open document a single in-memory server that is the authority for that file while anyone is editing it.
Every editor holds a WebSocket connection to that server (the Real-time Updates pattern). Clients send their changes to the server; the server applies them to its in-memory copy, decides the outcome of any conflict, and broadcasts the result back to everyone in the room. Because one server sees every change for a document, it can impose a single, consistent order without any distributed-consensus machinery. The document is assigned to a server when the first person opens it, and reassigned if that server fails or the file goes idle and is later reopened.
This is the same insight as Figma’s conceptual cousins (and the dealing-with-contention lesson): when one hot object needs strong consistency, routing all of its writes through a single owner is far simpler than coordinating many.
Why not full Operational Transform
OT, the algorithm behind Google Docs, is built for text — it transforms concurrent character insertions and deletions so everyone converges on the same string. Figma’s document is not text; it is a tree of objects with discrete properties. So Figma deliberately chose a simpler model tuned to that structure:
- Different objects, or different properties of the same object, never conflict. If you move a rectangle while I recolor it, both changes apply — they touch independent fields.
- The same property changed at the same time resolves by last-writer-wins. If we both drag the same shape, the server’s ordering picks a winner; the loser’s value is simply overwritten. For a design tool this is acceptable and even intuitive — one of us “won” the drag.
- Tree-structure edits (reparenting, ordering) get targeted rules so two people can’t, say, make two objects each other’s parent.
The result behaves like a set of per-property registers reconciled by a single authority — much of the convergence guarantee of a CRDT, without the general-purpose machinery, because the data model constrains what conflicts are even possible. The interview lesson is sharp: pick the weakest consistency model that still feels correct for your data. Figma did not need character-level merging, so it did not pay for it.
Persistence and recovery
The in-memory server is fast but volatile, so durability is a separate concern:
- The server periodically writes a snapshot of the document to object storage, plus the recent change log, so a crash loses at most a few seconds of edits.
- On reconnect, a client tells the server the last update it saw; the server replays everything since (the backfill / catch-up step every real-time system needs), so a brief network blip never loses work.
- When everyone closes the file, the final state is flushed to durable storage and the in-memory server is freed for another document.
Scaling
Scale comes from the fact that documents are independent. Figma shards by document: a routing layer maps each file to the server currently hosting it, and capacity grows by adding servers, each owning a subset of the active documents. A single monstrously large or massively-collaborated file is the hard case (one server, many connections) — handled by keeping the per-document data structures efficient and the per-change work small, the same way the live-comments design handles a viral stream.
What to take from this
- A single authority per hot object turns a hard distributed-consistency problem into a simple ordering problem — when the object fits in one server’s memory, this is often the right call.
- The data model picks the algorithm. Text wants OT/CRDT; a tree of independent properties wants per-property last-writer-wins. Don’t reach for the heavier tool than your data requires.
- Separate speed from durability. Serve edits from memory for latency; snapshot to object storage for safety; replay a change log on reconnect.
Key takeaways:
- Each open document has one in-memory authoritative server; all editors connect to it over WebSockets.
- Figma skips full text OT because its document is a tree of objects — conflicts resolve per-property by last-writer-wins, which is simpler and fits the data.
- Durability is decoupled: periodic snapshots to object storage plus a replayable change log for reconnecting clients.
- Scale by sharding documents across servers; the routing layer maps each file to its current owner.
- The transferable idea: route a hot object’s writes through a single owner, and choose the lightest consistency model your data allows.
