Shared Object Channels
Shared Object Channels in ART provide real-time collaborative editing capabilities using CRDT (Conflict-free Replicated Data Types) technology. These channels enable multiple users to simultaneously edit the same data structure with automatic conflict resolution and real-time synchronization.
Unlike regular messaging channels that send discrete messages, shared object channels maintain a synchronized data structure that multiple clients can edit simultaneously. Think of it like Google Docs for any object, changes made by one user are instantly reflected for all other users.
Key Features:
- 
CRDT-Based Synchronization: Uses advanced conflict-free replicated data types
 - 
Real-time Updates: Changes propagate instantly to all connected clients
 - 
Conflict Resolution: Automatic handling of concurrent edits without data loss
 - 
RGA Arrays: Replicated Growable Arrays for ordered list operations
 - 
Echo Suppression: Prevents infinite loops from your own changes
 
How Shared Object Channels Work
Shared Object Channels operate through a sophisticated CRDT (Conflict-free Replicated Data Types) system that maintains synchronized state across multiple clients. When you subscribe to a shared object channel, ART creates a live data structure that automatically synchronizes changes between all connected users in real-time.
Subscribing to Shared Object Channels
Subscribing to a shared object channel is identical to regular channels
- JavaScript
 
// Subscribe to shared object channel
const subscription = await adk.subscribe('YOUR_SHARED_OBJECT_CHANNEL');
The system initializes with any existing state from the server and creates a unique replica ID for your client to handle conflict resolution.
Accessing the Shared State
The core of shared object channels is the state() method, which returns a JavaScript Proxy object that behaves like a regular object but automatically synchronizes changes:
- JavaScript
 
// Get the shared state object
const sharedState = subscription.state();
// Now you can work with it like a regular JavaScript object
sharedState.title = "New Document Title"; // Access and modify properties
// Safe delete (no error if the key doesn't exist)
delete sharedState.name; 
This proxy object intercepts all property access and modifications, converting them into CRDT operations that are synchronized across all connected clients.
Working with Arrays
Shared object channels provide full array support using RGA (Replicated Growable Array) semantics, which handle concurrent insertions and deletions correctly
- JavaScript
 
const state = subscription.state();
// Create and manipulate arrays
state.items = [];
// Standard array operations work seamlessly
state.items.push("First item");
state.items.splice(1, 1, "Replaced item");
const removed = state.items.pop();
The RGA implementation ensures that concurrent array operations from different users are resolved consistently, maintaining the intended order even when users edit simultaneously.
Manual Synchronization Control
While changes are automatically synchronized, you can control when operations are sent to the server using the flush() method
- JavaScript
 
const state = liveDoc.state();
// Make multiple changes
state.title = "New Title";
state.content = "Updated content";
// Manually trigger synchronization
// All changes are batched and sent as a single operation
await subscription.flush();
By default, ART batches operations with a 50ms delay to optimize network usage, but flush() allows immediate synchronization when needed.
Listening to updates
The query() method allows you to observe specific parts of the shared object, useful for optimizing updates in large data structures:
- JavaScript
 
// Query specific path in the object
const titleQuery = subscription.query('document.title');
// Get current value without listening continuously
const currentTitle = await titleQuery.execute();
console.log(currentTitle); // Current title value
// Listen for changes to specific path
const unsubscribe = await titleQuery.listen((newTitle) => {
  console.log('Title changed to:', newTitle);
});
This targeted observation reduces unnecessary updates and improves performance in applications with complex shared state.