A host can hold more than one document. A chat keeps one per message. A game keeps one per player. Each client gets the ones it asks for, and patches for those only. A long thread stays fast on a phone that follows the last fifty messages, not all ten thousand.
Some documents live only as long as one connection: a cursor, a selection, a viewport. They go away when the client does.
Keyed documents belong to a protocol both sides register. The host mounts one per key; a command adds it to its caller with this.attach.include and takes it away with exclude. this.attach.mount adds one that lives only as long as the connection.
const host = getStateHost(state)!;
host.mount("player", { x: 0, y: 0 }, { key: ["ada"] });
const commands = useStatewireCommands({
follow(player: string) {
this.attach.include("player", [player]);
},
});Filters
Two people can attach to the same document and see different things. A read filter runs once per client and document, and redacts what that client receives. An owner sees the model's reasoning; a viewer gets null in its place.
- Rules: keep,
null, pick fields or omit fields. - Clients that share a filter share its work: it runs once per update for all of them.
- Filters cover snapshots and patches. Command results are sent to their caller unfiltered.
- When a role changes, reconnect that client and the new filter applies.