Encrypted chat × Interocitor
Two trusted clients. One blind mailbox.
Alice and Bob share a mesh key. Each message is encrypted before the in-page mailbox receives it and decrypted only by the two clients. Send a message, then inspect the stored envelope yourself.
Alice
Bob
What “last 15” means
The application owns message retention.
After a send, the writing client deletes visible rows older than the newest fifteen, synchronizes those CRDT tombstones, and compacts covered history. This limits chat content; it is separate from Interocitor’s time-based mailbox retention policy. Reloading resets this in-memory demonstration.
The minimal shape
Illustrative excerpt: the shared mesh key, stores, and fifteen-message pruning are omitted. The linked TypeScript source is the complete runnable demo.
const schema = {
tables: {
messages: {
fields: {
id: types.string,
sender: types.string,
body: types.string,
createdAt: types.index(types.number)
}
}
}
} satisfies DatabaseSchemaDefinition<ChatDB>;
const messages = db.table("messages");
await messages.put(id, { id, sender, body, createdAt: Date.now() });
await db.flush();
await peer.pull();
Read the full chat source →