/** * Moves the chat's unread state to the server, so that it survives a reload * and agrees across tabs and devices. `users.chat_read_at` holds the time of * the newest message the user has seen. * * It also replaces the index on `created_at` with one on `(created_at, id)`, * which the history now pages on, so that two messages from the same * millisecond can't fall between two pages. * * @module */ import type { DatabaseSync } from "node:sqlite"; /** * Run once by `runMigrations`. Existing users start with every message read, * instead of the whole history unread. A user created later starts with a * NULL `chat_read_at`, which chat-service reads as the user's creation time. */ export function up(db: DatabaseSync): void { const cols = db.prepare(`PRAGMA table_info(users);`).all() as { name: string; }[]; if (!cols.some((c) => c.name === "chat_read_at")) { db.exec(`ALTER TABLE users ADD COLUMN chat_read_at TEXT;`); db.prepare(`UPDATE users SET chat_read_at = ?;`).run( new Date().toISOString(), ); } db.exec(`DROP INDEX IF EXISTS idx_chat_messages_created;`); db.exec( `CREATE INDEX IF NOT EXISTS idx_chat_messages_created_id ON chat_messages(created_at, id);`, ); }