refactor: remove dead code across server, templ pages, and client modules
Deadcode-verified removals (RTA reachability from main, cross-checked with -test and textual xrefs): Go server: - whole files: middleware/transaction.go, middleware/error_handler.go, middleware/password_validator.go (live registration machinery kept), handlers/sync.go, sync/offline.go - unrouted endpoints: auth UpdateUsername/UpdateEmail, timezone settings handler, OPDS RegisterOPDS, Kobo LibrarySync handler, ReaderHandler.ShowReader, JSON-data twins on collections/library - duplicate book-matching handlers (book_matching.go Handler twins, matching.go MatchingHandler twins), superseded helpers (router.parseUUID, handlers.ValidateDeviceToken, normalizePath, userExists, generateLockID) Templ/client: - never-routed pages: api_explorer.templ, queue.templ and their client modules api-explorer.ts, api-explorer-docs.ts, queue.ts - fully orphaned wrapper modules events.ts, dom.ts - broken clearSyncQueue (called a nonexistent endpoint) and the hidden, never-populated sync-queue section on the devices page - 166+ unused exports demoted to private (knip-verified); ~85 truly dead declarations removed via tsc noUnusedLocals fixpoint - stale 'interactive API Explorer' claims dropped from docs The docs drift-gate package (internal/docs), templ-bound modules (dashboard, stats, header, index, login, profile*, bookshelf, collections, toast-error), sqlc-generated code, and web/static are intentionally untouched.
This commit is contained in:
1 parent
8733e83f1f
commit
8631aa00bf
107 files changed
+689
-3443
No files matched your search
@@ -1,7 +1,6 @@
|
||||
package main
|
||||
|
||||
import (
|
||||
"bookhoard/internal/database"
|
||||
"bookhoard/internal/handlers"
|
||||
"bytes"
|
||||
"context"
|
||||
@@ -11,7 +10,6 @@ import (
|
||||
"net/http/httptest"
|
||||
"testing"
|
||||
|
||||
"github.com/google/uuid"
|
||||
"github.com/jackc/pgx/v5/pgtype"
|
||||
"github.com/stretchr/testify/assert"
|
||||
"github.com/stretchr/testify/require"
|
||||
@@ -79,13 +77,3 @@ func TestWithStructs(t *testing.T) {
|
||||
assert.Equal(t, syncFreq, updatedDevice.SyncFrequencyMinutes.Int32, "DB: Sync frequency should be updated")
|
||||
})
|
||||
}
|
||||
|
||||
// verifyDeviceUpdated is a helper function for database verification after device updates
|
||||
func verifyDeviceUpdated(t *testing.T, db *database.Queries, deviceID uuid.UUID, syncEnabled bool, syncFreq int32) {
|
||||
pgDeviceID := pgtype.UUID{Bytes: [16]byte(deviceID), Valid: true}
|
||||
device, err := db.GetDevice(context.Background(), pgDeviceID)
|
||||
require.NoError(t, err, "Device should exist in database")
|
||||
|
||||
assert.Equal(t, syncEnabled, device.SyncEnabled.Bool, "DB: Sync enabled should match")
|
||||
assert.Equal(t, syncFreq, device.SyncFrequencyMinutes.Int32, "DB: Sync frequency should match")
|
||||
}
|
||||
@@ -53,7 +53,6 @@ func corruptItemColumn(t *testing.T, setup *TestServerSetup, itemID pgtype.UUID,
|
||||
require.Equal(t, int64(1), tag.RowsAffected(), "corruption must hit exactly the test item")
|
||||
}
|
||||
|
||||
|
||||
func setExtractorVersion(t *testing.T, setup *TestServerSetup, v int) {
|
||||
t.Helper()
|
||||
// Restore-to-prior (not a hardcoded value): the shared dev DB's
|
||||
|
||||
@@ -8,7 +8,6 @@ import (
|
||||
"io"
|
||||
"log"
|
||||
"net/http"
|
||||
"net/http/httptest"
|
||||
"testing"
|
||||
|
||||
"github.com/stretchr/testify/assert"
|
||||
@@ -268,9 +267,3 @@ func TestKoboDeviceHeaderParsing(t *testing.T) {
|
||||
assert.Equal(t, "4.38.23555", device.Firmware)
|
||||
})
|
||||
}
|
||||
|
||||
func closeTestServer(t *testing.T, ts interface{}, db interface{}) {
|
||||
if ts, ok := ts.(*httptest.Server); ok {
|
||||
ts.Close()
|
||||
}
|
||||
}
|
||||
@@ -88,7 +88,7 @@ func (s *OwnershipAndAdminTestSuite) createItemViaDB(withFolder bool) (itemID, l
|
||||
item, err := db.CreateMediaItem(ctx, database.CreateMediaItemParams{
|
||||
LibraryID: library.ID,
|
||||
Title: "Ownership Suite Item",
|
||||
Authors: []string{"Suite Author"},
|
||||
Authors: []string{"Suite Author"},
|
||||
FilePath: relPath,
|
||||
MimeType: pgtype.Text{String: "application/epub+zip", Valid: true},
|
||||
})
|
||||
@@ -101,18 +101,6 @@ func (s *OwnershipAndAdminTestSuite) TearDownSuite() {
|
||||
s.setup.Close()
|
||||
}
|
||||
|
||||
func (s *OwnershipAndAdminTestSuite) getItem(itemID string) map[string]interface{} {
|
||||
req, _ := http.NewRequest("GET", s.setup.Server.URL+"/api/media-items/"+itemID, nil)
|
||||
req.Header.Set("Authorization", "Bearer "+s.token)
|
||||
resp, err := (&http.Client{}).Do(req)
|
||||
require.NoError(s.T(), err)
|
||||
defer resp.Body.Close()
|
||||
require.Equal(s.T(), http.StatusOK, resp.StatusCode)
|
||||
var body map[string]interface{}
|
||||
require.NoError(s.T(), json.NewDecoder(resp.Body).Decode(&body))
|
||||
return body
|
||||
}
|
||||
|
||||
func (s *OwnershipAndAdminTestSuite) createHighlight(token string) map[string]interface{} {
|
||||
payload, _ := json.Marshal(map[string]interface{}{
|
||||
"selection_text": "owned annotation text",
|
||||
|
||||
@@ -22,7 +22,6 @@ import (
|
||||
func pFloat64(v float64) *float64 { return &v }
|
||||
func pStr(v string) *string { return &v }
|
||||
func pInt(v int) *int { return &v }
|
||||
func pInt64(v int64) *int64 { return &v }
|
||||
|
||||
func doReq(t *testing.T, method, url string, body interface{}, token string) *http.Response {
|
||||
t.Helper()
|
||||
|
||||
@@ -7,6 +7,7 @@ import (
|
||||
"testing"
|
||||
"time"
|
||||
|
||||
"github.com/go-playground/validator/v10"
|
||||
"github.com/labstack/echo/v5"
|
||||
"github.com/stretchr/testify/assert"
|
||||
)
|
||||
@@ -29,7 +30,13 @@ func TestPasswordComplexity(t *testing.T) {
|
||||
|
||||
for _, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
err := ratelimit.ValidatePassword(tt.password)
|
||||
// Exercise the live path: the passwordcomplex tag the auth request
|
||||
// structs use, registered exactly the way main.go registers it.
|
||||
v := validator.New()
|
||||
if err := ratelimit.RegisterPasswordValidation(v); err != nil {
|
||||
t.Fatalf("failed to register password validation: %v", err)
|
||||
}
|
||||
err := v.Var(tt.password, "required,passwordcomplex")
|
||||
if tt.valid {
|
||||
assert.NoError(t, err, "Password should be valid")
|
||||
} else {
|
||||
@@ -139,23 +146,3 @@ func TestRefreshTokenExpiration(t *testing.T) {
|
||||
expectedDuration := 7 * 24 * time.Hour
|
||||
assert.Equal(t, expectedDuration, 168*time.Hour, "Refresh token expiration is 7 days")
|
||||
}
|
||||
|
||||
// TestPasswordRequirementsList tests password requirements documentation
|
||||
func TestPasswordRequirementsList(t *testing.T) {
|
||||
requirements := ratelimit.GetPasswordRequirements()
|
||||
|
||||
assert.NotEmpty(t, requirements, "Password requirements list should not be empty")
|
||||
assert.Equal(t, 5, len(requirements), "Should have 5 password requirements")
|
||||
}
|
||||
|
||||
// TestDatabaseTransactionManager tests transaction manager creation
|
||||
func TestDatabaseTransactionManager(t *testing.T) {
|
||||
// Verify the transaction manager type exists
|
||||
assert.True(t, true, "Transaction manager structure verified")
|
||||
}
|
||||
|
||||
// TestErrorHandlingTypes tests error handling types
|
||||
func TestErrorHandlingTypes(t *testing.T) {
|
||||
// Verify error types exist
|
||||
assert.True(t, true, "Error handling types verified")
|
||||
}
|
||||
@@ -1,89 +1,20 @@
|
||||
package main
|
||||
|
||||
import (
|
||||
"bookhoard/internal/database"
|
||||
"bytes"
|
||||
"context"
|
||||
"encoding/json"
|
||||
"fmt"
|
||||
"io"
|
||||
"net/http"
|
||||
"net/http/httptest"
|
||||
"sync"
|
||||
"testing"
|
||||
|
||||
"github.com/google/uuid"
|
||||
"github.com/jackc/pgx/v5/pgtype"
|
||||
"github.com/stretchr/testify/assert"
|
||||
"github.com/stretchr/testify/require"
|
||||
)
|
||||
|
||||
// Helper functions for database verification and test utilities
|
||||
// These functions reduce code duplication and ensure consistent database state verification
|
||||
|
||||
// verifyDeviceCreated verifies a device exists in database with expected values
|
||||
func verifyDeviceCreated(t *testing.T, db *database.Queries, deviceID uuid.UUID, expectedName, expectedType, expectedIdentifier string) {
|
||||
pgDeviceID := pgtype.UUID{Bytes: [16]byte(deviceID), Valid: true}
|
||||
device, err := db.GetDevice(context.Background(), pgDeviceID)
|
||||
require.NoError(t, err, "Device should exist in database")
|
||||
|
||||
assert.Equal(t, expectedName, device.DeviceName, "Device name should match")
|
||||
assert.Equal(t, expectedType, device.DeviceType, "Device type should match")
|
||||
assert.Equal(t, expectedIdentifier, device.DeviceIdentifier, "Device identifier should match")
|
||||
assert.NotEmpty(t, device.AuthToken, "Device should have auth token")
|
||||
}
|
||||
|
||||
// verifyDeviceDeleted verifies a device does not exist in database
|
||||
func verifyDeviceDeleted(t *testing.T, db *database.Queries, deviceID uuid.UUID) {
|
||||
pgDeviceID := pgtype.UUID{Bytes: [16]byte(deviceID), Valid: true}
|
||||
_, err := db.GetDevice(context.Background(), pgDeviceID)
|
||||
assert.Error(t, err, "Device should be deleted from database")
|
||||
}
|
||||
|
||||
// verifyUserField verifies a user has expected field value in database
|
||||
func verifyUserField(t *testing.T, db *database.Queries, userID uuid.UUID, field string, expected interface{}) {
|
||||
pgUserID := pgtype.UUID{Bytes: [16]byte(userID), Valid: true}
|
||||
user, err := db.GetUser(context.Background(), pgUserID)
|
||||
require.NoError(t, err, "User should exist in database")
|
||||
|
||||
switch field {
|
||||
case "email":
|
||||
if em, ok := expected.(string); ok {
|
||||
assert.Equal(t, em, user.Email, "Email should match")
|
||||
}
|
||||
case "first_name":
|
||||
if fn, ok := expected.(string); ok {
|
||||
assert.Equal(t, fn, user.FirstName.String, "First name should match")
|
||||
}
|
||||
case "last_name":
|
||||
if ln, ok := expected.(string); ok {
|
||||
assert.Equal(t, ln, user.LastName.String, "Last name should match")
|
||||
}
|
||||
case "username":
|
||||
if un, ok := expected.(string); ok {
|
||||
assert.Equal(t, un, user.Username, "Username should match")
|
||||
}
|
||||
case "theme":
|
||||
if th, ok := expected.(string); ok {
|
||||
assert.Equal(t, th, user.Theme.String, "Theme should match")
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// verifyMediaItemInDB verifies a media item exists in database
|
||||
func verifyMediaItemInDB(t *testing.T, db *database.Queries, mediaID uuid.UUID) {
|
||||
pgMediaID := pgtype.UUID{Bytes: [16]byte(mediaID), Valid: true}
|
||||
_, err := db.GetMediaItem(context.Background(), pgMediaID)
|
||||
require.NoError(t, err, "Media item should exist in database")
|
||||
}
|
||||
|
||||
// verifyMediaItemDeleted verifies a media item does not exist in database
|
||||
func verifyMediaItemDeleted(t *testing.T, db *database.Queries, mediaID uuid.UUID) {
|
||||
pgMediaID := pgtype.UUID{Bytes: [16]byte(mediaID), Valid: true}
|
||||
_, err := db.GetMediaItem(context.Background(), pgMediaID)
|
||||
assert.Error(t, err, "Media item should be deleted from database")
|
||||
}
|
||||
|
||||
// createTestLibraryWithFolder creates a test library with optional folder
|
||||
func createTestLibraryWithFolder(t *testing.T, ts *httptest.Server, token, name string, withFolder bool) string {
|
||||
libReq := map[string]interface{}{
|
||||
@@ -141,36 +72,3 @@ func createTestLibraryWithFolder(t *testing.T, ts *httptest.Server, token, name
|
||||
|
||||
return libraryID
|
||||
}
|
||||
|
||||
// runConcurrent executes functions concurrently and waits for all to complete
|
||||
func runConcurrent(t *testing.T, maxConcurrent int, fns []func() error) []error {
|
||||
if len(fns) == 0 {
|
||||
return nil
|
||||
}
|
||||
if len(fns) < maxConcurrent {
|
||||
maxConcurrent = len(fns)
|
||||
}
|
||||
|
||||
errors := make(chan error, len(fns))
|
||||
var wg sync.WaitGroup
|
||||
|
||||
for i := 0; i < maxConcurrent; i++ {
|
||||
wg.Add(1)
|
||||
go func(idx int) {
|
||||
defer wg.Done()
|
||||
if err := fns[idx](); err != nil {
|
||||
errors <- err
|
||||
}
|
||||
}(i)
|
||||
}
|
||||
|
||||
wg.Wait()
|
||||
close(errors)
|
||||
|
||||
var allErrors []error
|
||||
for err := range errors {
|
||||
allErrors = append(allErrors, err)
|
||||
}
|
||||
|
||||
return allErrors
|
||||
}
|
||||
@@ -470,26 +470,6 @@ func (s *TestDeviceSetup) CreateLibrary(t *testing.T, name, libraryType string)
|
||||
return libraryUUID.String()
|
||||
}
|
||||
|
||||
// CreateCollection creates a test collection for the TestDeviceSetup
|
||||
func (s *TestDeviceSetup) CreateCollection(t *testing.T, name string) string {
|
||||
ctx := context.Background()
|
||||
|
||||
pgUserID := pgtype.UUID{Bytes: [16]byte(s.User.ID), Valid: true}
|
||||
collection, err := s.DB.CreateCollection(ctx, database.CreateCollectionParams{
|
||||
UserID: pgUserID,
|
||||
Name: name,
|
||||
Description: pgtype.Text{String: "Test collection description", Valid: true},
|
||||
Color: pgtype.Text{String: "#FF5733", Valid: true},
|
||||
Icon: pgtype.Text{String: "folder", Valid: true},
|
||||
})
|
||||
require.NoError(t, err, "Should create collection")
|
||||
|
||||
collectionUUID, err := uuid.FromBytes(collection.ID.Bytes[0:16])
|
||||
require.NoError(t, err, "Should parse collection ID")
|
||||
|
||||
return collectionUUID.String()
|
||||
}
|
||||
|
||||
// setupTestServer creates a test server with a test database
|
||||
// Returns: *TestServerSetup with automatic cleanup via t.Cleanup
|
||||
func setupTestServer(t *testing.T) *TestServerSetup {
|
||||
|
||||
@@ -14,7 +14,6 @@ import (
|
||||
"github.com/jackc/pgx/v5/pgtype"
|
||||
"github.com/stretchr/testify/assert"
|
||||
"github.com/stretchr/testify/require"
|
||||
"golang.org/x/crypto/bcrypt"
|
||||
)
|
||||
|
||||
// ensureSingleAdmin makes the "last admin" precondition deterministic in
|
||||
@@ -668,8 +667,3 @@ func TestUpdatePasswordSelfChange(t *testing.T) {
|
||||
assert.Contains(t, rec.Body.String(), "current password required")
|
||||
})
|
||||
}
|
||||
|
||||
func verifyPasswordHash(t *testing.T, hashedPassword, password string) {
|
||||
err := bcrypt.CompareHashAndPassword([]byte(hashedPassword), []byte(password))
|
||||
assert.NoError(t, err, "Password should match hash")
|
||||
}
|
||||
Reference in new issue
Block a user