Add unit tests for models and services
- 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.
This commit is contained in:
141
test/helpers/auth.helper.ts
Normal file
141
test/helpers/auth.helper.ts
Normal file
@@ -0,0 +1,141 @@
|
||||
/**
|
||||
* Authentication test helper - creates test users, tokens, and sessions
|
||||
*/
|
||||
|
||||
import { User } from '../../ts/models/user.ts';
|
||||
import { ApiToken } from '../../ts/models/apitoken.ts';
|
||||
import { AuthService } from '../../ts/services/auth.service.ts';
|
||||
import { TokenService } from '../../ts/services/token.service.ts';
|
||||
import type { TRegistryProtocol, ITokenScope, TUserStatus } from '../../ts/interfaces/auth.interfaces.ts';
|
||||
import { testConfig } from '../test.config.ts';
|
||||
|
||||
const TEST_PASSWORD = 'TestPassword123!';
|
||||
|
||||
export interface ICreateTestUserOptions {
|
||||
email?: string;
|
||||
username?: string;
|
||||
password?: string;
|
||||
displayName?: string;
|
||||
status?: TUserStatus;
|
||||
isPlatformAdmin?: boolean;
|
||||
emailVerified?: boolean;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a test user with sensible defaults
|
||||
*/
|
||||
export async function createTestUser(
|
||||
overrides: ICreateTestUserOptions = {}
|
||||
): Promise<{ user: User; password: string }> {
|
||||
const uniqueId = crypto.randomUUID().slice(0, 8);
|
||||
const password = overrides.password || TEST_PASSWORD;
|
||||
const passwordHash = await User.hashPassword(password);
|
||||
|
||||
const user = await User.createUser({
|
||||
email: overrides.email || `test-${uniqueId}@example.com`,
|
||||
username: overrides.username || `testuser-${uniqueId}`,
|
||||
passwordHash,
|
||||
displayName: overrides.displayName || `Test User ${uniqueId}`,
|
||||
});
|
||||
|
||||
// Set additional properties
|
||||
user.status = overrides.status || 'active';
|
||||
user.emailVerified = overrides.emailVerified ?? true;
|
||||
if (overrides.isPlatformAdmin) {
|
||||
user.isPlatformAdmin = true;
|
||||
}
|
||||
await user.save();
|
||||
|
||||
return { user, password };
|
||||
}
|
||||
|
||||
/**
|
||||
* Create admin user
|
||||
*/
|
||||
export async function createAdminUser(): Promise<{ user: User; password: string }> {
|
||||
return createTestUser({ isPlatformAdmin: true });
|
||||
}
|
||||
|
||||
/**
|
||||
* Login and get tokens
|
||||
*/
|
||||
export async function loginUser(
|
||||
email: string,
|
||||
password: string
|
||||
): Promise<{ accessToken: string; refreshToken: string; sessionId: string }> {
|
||||
const authService = new AuthService({
|
||||
jwtSecret: testConfig.jwt.secret,
|
||||
});
|
||||
|
||||
const result = await authService.login(email, password, {
|
||||
userAgent: 'TestAgent/1.0',
|
||||
ipAddress: '127.0.0.1',
|
||||
});
|
||||
|
||||
if (!result.success) {
|
||||
throw new Error(`Login failed: ${result.errorMessage}`);
|
||||
}
|
||||
|
||||
return {
|
||||
accessToken: result.accessToken!,
|
||||
refreshToken: result.refreshToken!,
|
||||
sessionId: result.sessionId!,
|
||||
};
|
||||
}
|
||||
|
||||
export interface ICreateTestApiTokenOptions {
|
||||
userId: string;
|
||||
name?: string;
|
||||
protocols?: TRegistryProtocol[];
|
||||
scopes?: ITokenScope[];
|
||||
organizationId?: string;
|
||||
expiresInDays?: number;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create test API token
|
||||
*/
|
||||
export async function createTestApiToken(
|
||||
options: ICreateTestApiTokenOptions
|
||||
): Promise<{ rawToken: string; token: ApiToken }> {
|
||||
const tokenService = new TokenService();
|
||||
|
||||
return tokenService.createToken({
|
||||
userId: options.userId,
|
||||
organizationId: options.organizationId,
|
||||
name: options.name || `test-token-${crypto.randomUUID().slice(0, 8)}`,
|
||||
protocols: options.protocols || ['npm', 'oci'],
|
||||
scopes: options.scopes || [
|
||||
{
|
||||
protocol: '*',
|
||||
actions: ['read', 'write', 'delete'],
|
||||
},
|
||||
],
|
||||
expiresInDays: options.expiresInDays,
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Create auth header for API requests
|
||||
*/
|
||||
export function createAuthHeader(token: string): { Authorization: string } {
|
||||
return { Authorization: `Bearer ${token}` };
|
||||
}
|
||||
|
||||
/**
|
||||
* Create basic auth header (for registry protocols)
|
||||
*/
|
||||
export function createBasicAuthHeader(
|
||||
username: string,
|
||||
password: string
|
||||
): { Authorization: string } {
|
||||
const credentials = btoa(`${username}:${password}`);
|
||||
return { Authorization: `Basic ${credentials}` };
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the default test password
|
||||
*/
|
||||
export function getTestPassword(): string {
|
||||
return TEST_PASSWORD;
|
||||
}
|
||||
Reference in New Issue
Block a user