Give each handler and service test its own database (closes #131)
check / check (push) Waiting to run

Test databases in internal/handlers and internal/service were named
after the address of the running test. A later test could get the
address of a finished one, and with it a database that test's server
might still hold open. Each test database now gets a random name, as
in internal/ircserver.

A new test in each package opens two test databases at once and checks
that they do not share one; both new tests fail with the old names.

Model: opus-5-5
Co-authored-by: clawbot <sneak+clawbot@sneak.cloud>
This commit was merged in pull request #138.
This commit is contained in:
2026-10-20 13:04:40 +02:00
committed by clawbot
parent 5b430cf835
commit 4ab320ab2d
2 changed files with 48 additions and 4 deletions
+29 -2
View File
@@ -7,6 +7,7 @@ package handlers_test
import (
"bytes"
"context"
"crypto/rand"
"database/sql"
"encoding/json"
"errors"
@@ -152,9 +153,12 @@ func newTestServerWith(
) *testServer {
t.Helper()
// A random name, so that no other test can share it, not
// even one that has finished but still holds its database
// open.
dbURL := fmt.Sprintf(
"file:test_%p?mode=memory&cache=shared",
t,
"file:%s?mode=memory&cache=shared",
rand.Text(),
)
copyTemplateDB(t, dbURL)
@@ -667,6 +671,29 @@ func TestCreateSessionDuplicate(t *testing.T) {
}
}
// TestEachTestServerHasItsOwnDatabase checks that starting a
// second test server leaves the first one's database alone and
// starts on an empty one of its own.
func TestEachTestServerHasItsOwnDatabase(t *testing.T) {
first := newTestServer(t)
first.createSession("samenick")
second := newTestServer(t)
resp := postSession(t, first, "samenick")
defer func() { _ = resp.Body.Close() }()
if resp.StatusCode != http.StatusConflict {
t.Fatalf(
"first server: expected 409, got %d",
resp.StatusCode,
)
}
second.createSession("samenick")
}
func TestCreateSessionEmpty(t *testing.T) {
tserver := newTestServer(t)
+19 -2
View File
@@ -6,6 +6,7 @@ package service_test
import (
"context"
"crypto/rand"
"encoding/json"
"errors"
"fmt"
@@ -43,9 +44,12 @@ type testEnv struct {
func newTestEnv(t *testing.T) *testEnv {
t.Helper()
// A random name, so that no other test can share it, not
// even one that has finished but still holds its database
// open.
dbURL := fmt.Sprintf(
"file:svc_test_%p?mode=memory&cache=shared",
t,
"file:%s?mode=memory&cache=shared",
rand.Text(),
)
var (
@@ -137,6 +141,19 @@ func createSession(
return sessionID
}
// TestEachTestEnvHasItsOwnDatabase checks that a test
// environment starts on an empty database while another one
// is still open.
func TestEachTestEnvHasItsOwnDatabase(t *testing.T) {
ctx := t.Context()
first := newTestEnv(t)
createSession(ctx, t, first.db, "samenick")
second := newTestEnv(t)
createSession(ctx, t, second.db, "samenick")
}
func TestFanOut(t *testing.T) {
env := newTestEnv(t)
ctx := t.Context()