- Implemented unit tests for the Package model, covering methods such as generateId, findById, findByName, and version management. - Created unit tests for the Repository model, including repository creation, name validation, and retrieval methods. - Added tests for the Session model, focusing on session creation, validation, and invalidation. - Developed unit tests for the User model, ensuring user creation, password hashing, and retrieval methods function correctly. - Implemented AuthService tests, validating login, token refresh, and session management. - Added TokenService tests, covering token creation, validation, and revocation processes.
107 lines
2.9 KiB
TypeScript
107 lines
2.9 KiB
TypeScript
/**
|
|
* Database test helper - manages test database lifecycle
|
|
*
|
|
* NOTE: The smartdata models use a global `db` singleton. This helper
|
|
* ensures proper initialization and cleanup for tests.
|
|
*/
|
|
|
|
import * as plugins from '../../ts/plugins.ts';
|
|
import { testConfig } from '../test.config.ts';
|
|
|
|
// Test database instance - separate from production
|
|
let testDb: plugins.smartdata.SmartdataDb | null = null;
|
|
let testDbName: string = '';
|
|
let isConnected = false;
|
|
|
|
// We need to patch the global db export since models reference it
|
|
// This is done by re-initializing with the test config
|
|
import { initDb, closeDb } from '../../ts/models/db.ts';
|
|
|
|
/**
|
|
* Initialize test database with unique name per test run
|
|
*/
|
|
export async function setupTestDb(config?: {
|
|
mongoUrl?: string;
|
|
dbName?: string;
|
|
}): Promise<void> {
|
|
// If already connected, reuse the connection
|
|
if (isConnected && testDb) {
|
|
return;
|
|
}
|
|
|
|
const mongoUrl = config?.mongoUrl || testConfig.mongodb.url;
|
|
|
|
// Generate unique database name for this test session
|
|
const uniqueId = crypto.randomUUID().slice(0, 8);
|
|
testDbName = config?.dbName || `${testConfig.mongodb.name}-${uniqueId}`;
|
|
|
|
// Initialize the global db singleton with test configuration
|
|
testDb = await initDb(mongoUrl, testDbName);
|
|
isConnected = true;
|
|
}
|
|
|
|
/**
|
|
* Clean up test database - deletes all documents from collections
|
|
* This is safer than dropping collections which causes index rebuild issues
|
|
*/
|
|
export async function cleanupTestDb(): Promise<void> {
|
|
if (!testDb || !isConnected) return;
|
|
|
|
try {
|
|
const collections = await testDb.mongoDb.listCollections().toArray();
|
|
for (const col of collections) {
|
|
// Delete all documents but preserve indexes
|
|
await testDb.mongoDb.collection(col.name).deleteMany({});
|
|
}
|
|
} catch (error) {
|
|
console.warn('[TestHelper] Error cleaning database:', error);
|
|
}
|
|
}
|
|
|
|
/**
|
|
* Teardown test database - drops database and closes connection
|
|
*/
|
|
export async function teardownTestDb(): Promise<void> {
|
|
if (!testDb || !isConnected) return;
|
|
|
|
try {
|
|
// Drop the test database
|
|
await testDb.mongoDb.dropDatabase();
|
|
// Close the connection
|
|
await closeDb();
|
|
testDb = null;
|
|
isConnected = false;
|
|
} catch (error) {
|
|
console.warn('[TestHelper] Error tearing down database:', error);
|
|
}
|
|
}
|
|
|
|
/**
|
|
* Clear specific collection(s) - deletes all documents
|
|
*/
|
|
export async function clearCollections(...collectionNames: string[]): Promise<void> {
|
|
if (!testDb || !isConnected) return;
|
|
|
|
for (const name of collectionNames) {
|
|
try {
|
|
await testDb.mongoDb.collection(name).deleteMany({});
|
|
} catch {
|
|
// Collection may not exist, ignore
|
|
}
|
|
}
|
|
}
|
|
|
|
/**
|
|
* Get the current test database name
|
|
*/
|
|
export function getTestDbName(): string {
|
|
return testDbName;
|
|
}
|
|
|
|
/**
|
|
* Get the database instance for direct access
|
|
*/
|
|
export function getTestDb(): plugins.smartdata.SmartdataDb | null {
|
|
return testDb;
|
|
}
|