Files

80 lines
2.9 KiB
TypeScript

import { describe, expect, test } from "bun:test"
import { mkdtemp, rm } from "node:fs/promises"
import { tmpdir } from "node:os"
import { join } from "node:path"
import { Effect } from "effect"
import { SqlClient } from "effect/sql"
import { sqliteLayer } from "@opencode/core/database/sqlite.bun"
const node = Bun.which("node")
// Skipped on Windows for the same Bun.build panic as sqlite-bundle.test.ts.
describe.skipIf(process.platform === "win32" || !node)("node sqlite client", () => {
test("boots migrations, commits drizzle transactions and types constraint errors", async () => {
const dir = await mkdtemp(join(tmpdir(), "sqlite-node-"))
try {
const build = await Bun.build({
entrypoints: [join(import.meta.dir, "fixture/sqlite-node-client.ts")],
target: "node",
conditions: ["node"],
outdir: join(dir, "bundle"),
throw: false,
})
expect(build.logs).toEqual([])
expect(build.success).toBe(true)
const output = await build.outputs[0].text()
expect(output).not.toContain("bun:sqlite")
const child = Bun.spawn([node!, build.outputs[0].path, dir], { stdout: "pipe", stderr: "pipe" })
const [stdout, stderr, code] = await Promise.all([
new Response(child.stdout).text(),
new Response(child.stderr).text(),
child.exited,
])
expect({ code, stderr: code === 0 ? "" : stderr }).toEqual({ code: 0, stderr: "" })
expect(JSON.parse(stdout.trim().split("\n").at(-1)!)).toEqual({
journal: "wal",
reason: "ConstraintError",
rows: 2,
inserted: [{ id: 1, name: "Ada" }],
duplicate: "EffectDrizzleQueryError",
afterFailure: [{ id: 1, name: "Ada" }],
raw: 1,
leakedTransaction: [],
leakedReserve: [],
})
} finally {
await rm(dir, { recursive: true, force: true })
}
}, 30_000)
})
describe("bun sqlite client", () => {
test("types constraint errors and opens read-only", async () => {
const dir = await mkdtemp(join(tmpdir(), "sqlite-bun-"))
const filename = join(dir, "probe.db")
try {
const reason = await Effect.runPromise(
Effect.gen(function* () {
const sql = yield* SqlClient.SqlClient
yield* sql`CREATE TABLE probe (id TEXT PRIMARY KEY)`
yield* sql`INSERT INTO probe (id) VALUES ('a')`
const error = yield* sql`INSERT INTO probe (id) VALUES ('a')`.pipe(Effect.flip)
return error.reason._tag
}).pipe(Effect.provide(sqliteLayer({ filename }))),
)
expect(reason).toBe("ConstraintError")
const rows = await Effect.runPromise(
Effect.gen(function* () {
const sql = yield* SqlClient.SqlClient
return yield* sql<{ id: string }>`SELECT id FROM probe`
}).pipe(Effect.provide(sqliteLayer({ filename, readonly: true }))),
)
expect(rows).toEqual([{ id: "a" }])
} finally {
await rm(dir, { recursive: true, force: true })
}
})
})