import { Database } from "bun:sqlite";
import { describe, expect, test } from "bun:test";
import { ScopedStore } from "./store";
/** Just enough of DurableObjectStorage for ScopedStore, on bun:sqlite. */
function fakeStorage() {
const db = new Database(":memory:");
const kv = new Map<string, unknown>();
const sql = {
exec(query: string, ...params: unknown[]) {
const statement = db.query(query);
const rows = /^\s*(SELECT|PRAGMA|WITH)/i.test(query) ? (statement.all(...(params as never[])) as unknown[]) : [];
if (rows.length === 0 && !/^\s*(SELECT|WITH)/i.test(query)) statement.run(...(params as never[]));
return {
toArray: () => rows,
one: () => {
if (rows.length !== 1) throw new Error("expected one row");
return rows[0];
},
};
},
};
return {
sql,
get: async (key: string) => kv.get(key),
put: async (key: string, value: unknown) => void kv.set(key, value),
deleteAll: async () => kv.clear(),
transactionSync: <T>(fn: () => T) => db.transaction(fn)(),
} as unknown as DurableObjectStorage;
}
const SCHEMA = ["CREATE TABLE IF NOT EXISTS items (id TEXT PRIMARY KEY, title TEXT)"];
describe("ScopedStore", () => {
test("applies the schema once and re-applies it when the DDL changes", async () => {
const storage = fakeStorage();
const store = new ScopedStore(storage, SCHEMA);
await store.prepare();
expect(store.run("INSERT INTO items VALUES ('a', 'one')", []).changes).toBe(1);
const grown = new ScopedStore(storage, [...SCHEMA, "CREATE TABLE IF NOT EXISTS tags (id TEXT PRIMARY KEY)"]);