Metadata
Mesh provides two types of metadata, both stored in Redis and available across all server instances:
- Connection metadata: tied to individual WebSocket connections
- Room metadata: tied to specific room names
Metadata is useful for attaching information like user IDs, roles, tokens, room settings, or custom fields relevant to your app.
Connection metadata
Attach structured data to a WebSocket connection, commonly used for:
- User identification (e.g.
userId
,role
) - Session tokens
- Enriching presence events
await ..(connection, {
: "user123",
: "admin",
});
Update strategies
Connection metadata supports three update strategies:
// Replace entire metadata (default)
await ..(connection, {
: "user123",
: "admin",
});
// Merge with existing metadata at the top level
await ..(connection, {
: "moderator", // This will update the role while preserving userId
}, { : "merge" });
// Deep merge - recursively merges nested objects
await ..(connection, {
: { : "dark" }, // This will merge with existing preferences
}, { : "deepMerge" });
You can read metadata later:
const = await ..(connection);
// or by connection ID:
const = await ..("conn123");
Connection metadata is automatically removed when the connection closes.
Room metadata
Store structured info about a room, like:
- Topics or settings
- Ownership and access rules
- Game or session state
await ..("lobby", {
: "General Discussion",
: "user123",
});
Update strategies
Room metadata also supports three update strategies:
// Replace entire metadata (default)
await ..("lobby", {
: "General Discussion",
: "user123",
});
// Merge with existing metadata at the top level
await ..("lobby", {
: "Updated Topic", // This preserves createdBy while updating topic
}, { : "merge" });
// Deep merge - recursively merges nested objects
await ..("lobby", {
: {
: 100 // This merges with existing settings object
}
}, { : "deepMerge" });
To retrieve metadata:
const = await ..("lobby");
Room metadata is removed automatically when you call deleteRoom(...)
, or you can explicitly clear it by setting the value to null
.
Accessing metadata from clients
Clients can retrieve metadata directly using built-in client methods:
Connection metadata
const = await .("conn123");
.(.userId, .username);
Get your own connection metadata by omitting the connection ID:
const = await .();
.(.userId, .username);
Room metadata
const = await .("lobby");
.(.topic);
Best practices
- Keep metadata small. Avoid large or deeply nested objects.
- Don’t store sensitive data. Expose only what’s safe to read.
- Use
merge
strategy for partial updates when you want to preserve existing fields. - Use
deepMerge
strategy when working with nested objects that need partial updates. - Use consistent ID formats, e.g.
"lobby"
,"user:123"
.
See Server SDK → Metadata and Client SDK → Presence for advanced usage.