Fix test infrastructure and device UUID handling

- Remove manual device ID generation, use database-generated IDs
- Add comprehensive test helpers (setupTestServer, loginTestUser, getTestUserID)
- Add cleanup step for existing test users in integration tests
- Fix UUID parsing from database responses
This commit is contained in:
2026-01-30 20:16:19 -05:00
parent 0e784f6d3f
commit 95fe849eeb
3 changed files with 239 additions and 21 deletions
+23 -21
View File
@@ -3,12 +3,12 @@ package main
import (
"bookmann/internal/database"
"bytes"
"context"
"encoding/json"
"fmt"
"net/http"
"net/http/httptest"
"testing"
"time"
"github.com/google/uuid"
"github.com/jackc/pgx/v5/pgtype"
@@ -16,7 +16,7 @@ import (
)
func TestDeviceRegistrationFlow(t *testing.T) {
_, _, _, ts := setupTestServer(t)
ts, _, _, _ := setupTestServer(t)
defer ts.Close()
// Step 1: Initiate device registration
@@ -115,7 +115,7 @@ func TestDeviceRegistrationFlow(t *testing.T) {
}
func TestListDevices(t *testing.T) {
db, _, _, ts := setupTestServer(t)
ts, db, _, _ := setupTestServer(t)
defer ts.Close()
// Login to get token
@@ -123,11 +123,9 @@ func TestListDevices(t *testing.T) {
// Create a device directly in the database
userID := getTestUserID(t, db)
deviceID := uuid.New()
deviceToken := fmt.Sprintf("dev_%s", uuid.New().String())
_, err := db.CreateDevice(context.Background(), database.CreateDeviceParams{
ID: pgtype.UUID{Bytes: [16]byte(deviceID), Valid: true},
UserID: pgtype.UUID{Bytes: [16]byte(userID), Valid: true},
DeviceName: "Test Device",
DeviceType: "koreader",
@@ -162,7 +160,7 @@ func TestListDevices(t *testing.T) {
}
func TestUpdateDevice(t *testing.T) {
db, _, _, ts := setupTestServer(t)
ts, db, _, _ := setupTestServer(t)
defer ts.Close()
// Login to get token
@@ -170,11 +168,9 @@ func TestUpdateDevice(t *testing.T) {
// Create a device directly in the database
userID := getTestUserID(t, db)
deviceID := uuid.New()
deviceToken := fmt.Sprintf("dev_%s", uuid.New().String())
_, err := db.CreateDevice(context.Background(), database.CreateDeviceParams{
ID: pgtype.UUID{Bytes: [16]byte(deviceID), Valid: true},
device, err := db.CreateDevice(context.Background(), database.CreateDeviceParams{
UserID: pgtype.UUID{Bytes: [16]byte(userID), Valid: true},
DeviceName: "Test Device",
DeviceType: "koreader",
@@ -187,6 +183,11 @@ func TestUpdateDevice(t *testing.T) {
})
assert.NoError(t, err, "Should create device")
// Get the device ID from the created device
deviceIDBytes := device.ID.Bytes[0:16]
deviceID, err := uuid.FromBytes(deviceIDBytes)
assert.NoError(t, err, "Should parse device ID")
// Update device
updateRequest := map[string]interface{}{
"device_name": "Updated Device Name",
@@ -208,14 +209,14 @@ func TestUpdateDevice(t *testing.T) {
assert.True(t, response["device_updated"].(bool), "Should confirm device updated")
device := response["device"].(map[string]interface{})
assert.Equal(t, "Updated Device Name", device["device_name"], "Should have updated name")
assert.Equal(t, false, device["sync_enabled"], "Should be disabled")
assert.Equal(t, int32(10), device["sync_frequency"], "Should have updated frequency")
updatedDevice := response["device"].(map[string]interface{})
assert.Equal(t, "Updated Device Name", updatedDevice["device_name"], "Should have updated name")
assert.Equal(t, false, updatedDevice["sync_enabled"], "Should be disabled")
assert.Equal(t, int32(10), updatedDevice["sync_frequency"], "Should have updated frequency")
}
func TestDeleteDevice(t *testing.T) {
db, _, _, ts := setupTestServer(t)
ts, db, _, _ := setupTestServer(t)
defer ts.Close()
// Login to get token
@@ -223,11 +224,9 @@ func TestDeleteDevice(t *testing.T) {
// Create a device directly in the database
userID := getTestUserID(t, db)
deviceID := uuid.New()
deviceToken := fmt.Sprintf("dev_%s", uuid.New().String())
_, err := db.CreateDevice(context.Background(), database.CreateDeviceParams{
ID: pgtype.UUID{Bytes: [16]byte(deviceID), Valid: true},
newDevice, err := db.CreateDevice(context.Background(), database.CreateDeviceParams{
UserID: pgtype.UUID{Bytes: [16]byte(userID), Valid: true},
DeviceName: "Test Device",
DeviceType: "koreader",
@@ -240,6 +239,11 @@ func TestDeleteDevice(t *testing.T) {
})
assert.NoError(t, err, "Should create device")
// Get the device ID from the created device
deviceIDBytes := newDevice.ID.Bytes[0:16]
deviceID, err := uuid.FromBytes(deviceIDBytes)
assert.NoError(t, err, "Should parse device ID")
// Delete device
req := httptest.NewRequest("DELETE", fmt.Sprintf("/api/devices/%s", deviceID.String()), nil)
req.Header.Set("Authorization", "Bearer "+token)
@@ -249,21 +253,19 @@ func TestDeleteDevice(t *testing.T) {
assert.Equal(t, http.StatusNoContent, rec.Code, "Should delete device")
// Verify device is deleted
_, err = db.GetDevice(context.Background(), pgtype.UUID{Bytes: [16]byte(deviceID), Valid: true})
_, err = db.GetDevice(context.Background(), newDevice.ID)
assert.Error(t, err, "Device should be deleted")
}
func TestDeviceAuthentication(t *testing.T) {
db, _, _, ts := setupTestServer(t)
ts, db, _, _ := setupTestServer(t)
defer ts.Close()
// Create a device directly in the database
userID := getTestUserID(t, db)
deviceID := uuid.New()
deviceToken := fmt.Sprintf("dev_%s", uuid.New().String())
_, err := db.CreateDevice(context.Background(), database.CreateDeviceParams{
ID: pgtype.UUID{Bytes: [16]byte(deviceID), Valid: true},
UserID: pgtype.UUID{Bytes: [16]byte(userID), Valid: true},
DeviceName: "Test Device",
DeviceType: "koreader",