package callstest import ( "context" "io" "log/slog" "path/filepath" "strings" "testing" "amadan.net/rastrillo/rastrillo/db" "amadan.net/oficina/calls/internal/calls" ) func openDB(t *testing.T) *db.DB { t.Helper() d, err := db.Open(filepath.Join(t.TempDir(), "app.db"), slog.New(slog.NewTextHandler(io.Discard, nil))) if err != nil { t.Fatal(err) } t.Cleanup(func() { d.Close() }) return d } // testCtx returns a context cancelled at the end of the test, so a // successful calls.App build's hourly sweep ticker does not outlive it // (Codex round 3, C3-2: App(context.Background(), ...) in a test leaves // a goroutine running against a database the test is about to close). func testCtx(t *testing.T) context.Context { t.Helper() ctx, cancel := context.WithCancel(context.Background()) t.Cleanup(cancel) return ctx } func TestProductionRefusesToStartWithoutSecrets(t *testing.T) { // validDEK is a valid 32-byte base64 DEK, used in the "no mailer" // and "no allowlist" cases so each refuses for its own named // reason rather than for a bad DEK. const validDEK = "AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA=" cases := map[string]calls.Config{ "no origin": {Env: "production"}, "no key": {Env: "production", Origin: "https://x.test"}, "no dek": {Env: "production", Origin: "https://x.test", InstanceKey: "k"}, "no mailer": {Env: "production", Origin: "https://x.test", InstanceKey: "k", DEK: validDEK}, "no allowlist": {Env: "production", Origin: "https://x.test", InstanceKey: "k", DEK: validDEK, Mailer: nopMailer{}}, } for name, cfg := range cases { if _, rt, err := calls.App(testCtx(t), openDB(t), cfg); err == nil { rt.Close() t.Errorf("%s: production started without it", name) } } } func TestDevelopmentStartsWithNothing(t *testing.T) { _, rt, err := calls.App(testCtx(t), openDB(t), calls.Config{Env: calls.EnvDevelopment}) if err != nil { t.Fatalf("development refused: %v", err) } t.Cleanup(rt.Close) } func TestBadDEKIsRefusedEvenInDevelopment(t *testing.T) { _, rt, err := calls.App(testCtx(t), openDB(t), calls.Config{Env: calls.EnvDevelopment, DEK: "not base64!"}) if err == nil { rt.Close() } if err == nil || !strings.Contains(err.Error(), "base64") { t.Fatalf("want a base64 refusal, got %v", err) } }