favoritter/internal/database/database_test.go

140 lines
3.1 KiB
Go
Raw Permalink Normal View History

// SPDX-License-Identifier: AGPL-3.0-or-later
package database
import (
"testing"
_ "modernc.org/sqlite"
)
func TestOpenInMemory(t *testing.T) {
db, err := Open(":memory:")
if err != nil {
t.Fatalf("Open(:memory:): %v", err)
}
defer db.Close()
// Verify the connection is usable.
var result int
if err := db.QueryRow("SELECT 1").Scan(&result); err != nil {
t.Fatalf("query: %v", err)
}
if result != 1 {
t.Errorf("SELECT 1 = %d", result)
}
}
func TestMigrateCreatesAllTables(t *testing.T) {
db, err := Open(":memory:")
if err != nil {
t.Fatalf("open: %v", err)
}
defer db.Close()
if err := Migrate(db); err != nil {
t.Fatalf("migrate: %v", err)
}
// Check that core tables exist.
tables := []string{"users", "faves", "tags", "fave_tags", "sessions", "site_settings", "schema_migrations", "signup_requests"}
for _, table := range tables {
var count int
err := db.QueryRow("SELECT COUNT(*) FROM sqlite_master WHERE type='table' AND name=?", table).Scan(&count)
if err != nil {
t.Errorf("check table %s: %v", table, err)
}
if count != 1 {
t.Errorf("table %s does not exist", table)
}
}
}
func TestMigrateIdempotent(t *testing.T) {
db, err := Open(":memory:")
if err != nil {
t.Fatalf("open: %v", err)
}
defer db.Close()
// First migration.
if err := Migrate(db); err != nil {
t.Fatalf("first migrate: %v", err)
}
// Second migration should be a no-op.
if err := Migrate(db); err != nil {
t.Fatalf("second migrate: %v", err)
}
// Verify schema_migrations has entries (no duplicates).
var count int
db.QueryRow("SELECT COUNT(*) FROM schema_migrations").Scan(&count)
if count < 1 {
t.Error("expected at least one migration record")
}
}
func TestPRAGMAs(t *testing.T) {
db, err := Open(":memory:")
if err != nil {
t.Fatalf("open: %v", err)
}
defer db.Close()
// WAL mode.
var journalMode string
db.QueryRow("PRAGMA journal_mode").Scan(&journalMode)
// In-memory databases use "memory" journal mode, not "wal".
// WAL is only meaningful for file-based databases.
// We just verify the pragma was accepted without error.
// Foreign keys should be ON.
var fk int
db.QueryRow("PRAGMA foreign_keys").Scan(&fk)
if fk != 1 {
t.Errorf("foreign_keys = %d, want 1", fk)
}
// Busy timeout.
var timeout int
db.QueryRow("PRAGMA busy_timeout").Scan(&timeout)
if timeout != 5000 {
t.Errorf("busy_timeout = %d, want 5000", timeout)
}
}
func TestSingleConnection(t *testing.T) {
db, err := Open(":memory:")
if err != nil {
t.Fatalf("open: %v", err)
}
defer db.Close()
stats := db.Stats()
if stats.MaxOpenConnections != 1 {
t.Errorf("MaxOpenConnections = %d, want 1", stats.MaxOpenConnections)
}
}
func TestSiteSettingsSeeded(t *testing.T) {
db, err := Open(":memory:")
if err != nil {
t.Fatalf("open: %v", err)
}
defer db.Close()
if err := Migrate(db); err != nil {
t.Fatalf("migrate: %v", err)
}
// Migrations should seed a default site_settings row.
var siteName string
err = db.QueryRow("SELECT site_name FROM site_settings WHERE id = 1").Scan(&siteName)
if err != nil {
t.Fatalf("query site_settings: %v", err)
}
if siteName == "" {
t.Error("expected non-empty default site_name")
}
}