Loro (CRDT) Collaboration
Real-time collaboration using Loro CRDTs
Installation
yarn add @rowsncolumns/loro loro-crdtnpm install @rowsncolumns/loro loro-crdtQuick Start
import { useLoro } from "@rowsncolumns/loro";
import { LoroDoc } from "loro-crdt";
// Create a Loro document
const loroDoc = new LoroDoc();
function SpreadsheetEditor() {
const [sheetData, setSheetData] = useState({});
const [sheets, setSheets] = useState([]);
const [tables, setTables] = useState([]);
const [sheetId, setSheetId] = useState(1);
const [activeCell, setActiveCell] = useState({ rowIndex: 1, columnIndex: 1 });
const { onBroadcastPatch, users, synced, isLeader, importUpdate } = useLoro({
doc: loroDoc,
userId: "user-123",
title: "John Doe",
sheetId,
activeCell,
initialSheets: [],
onChangeSheetData: setSheetData,
onChangeSheets: setSheets,
onChangeTables: setTables,
onChangeActiveSheet: setSheetId,
calculateNow,
enqueueGraphOperation: (op) => {
// Handle dependency graph updates for formula recalculation
},
onSyncUpdate: (update) => {
// Send update to server
websocket.send(update);
},
});
// Pass onBroadcastPatch to useSpreadsheetState
return <Spreadsheet sheetData={sheetData} sheets={sheets} users={users} />;
}Integration with useSpreadsheetState
Setting Up a Loro Sync Server
Basic Server
Server with Redis Persistence
Server with PostgreSQL Persistence
Document Structure
Cell Key Format
Key
Description
CellDataV3 Structure
Presence Awareness
Leader Election
Offline Support
Error Handling
Why Loro for Spreadsheets?
Comparison with ShareDB
Aspect
Loro (CRDT)
ShareDB (OT)
Why CRDTs Work Well for Spreadsheets
When to Choose Loro
When to Choose ShareDB
Last updated