fix: Major bug cleanup pass 1
All checks were successful
Queue Release Build / prepare (push) Successful in 19s
Deploy Web Apps / deploy (push) Successful in 8m12s
Queue Release Build / build-windows (push) Successful in 27m44s
Queue Release Build / build-linux (push) Successful in 48m1s
Queue Release Build / build-android (push) Successful in 22m7s
Queue Release Build / finalize (push) Successful in 2m42s

This commit is contained in:
2026-06-09 17:59:54 +02:00
parent 80d7728e66
commit eb51f043ac
127 changed files with 2731 additions and 322 deletions

View File

@@ -0,0 +1,30 @@
import {
describe,
it,
expect
} from 'vitest';
import { isDuplicateUsernameError } from './user-registration.rules';
describe('user-registration.rules', () => {
it('detects sqlite unique constraint failures on username', () => {
expect(isDuplicateUsernameError({
message: 'UNIQUE constraint failed: users.username'
})).toBe(true);
});
it('detects typeorm query failed errors with username constraint text', () => {
expect(isDuplicateUsernameError({
name: 'QueryFailedError',
message: 'SQLITE_CONSTRAINT: UNIQUE constraint failed: users.username'
})).toBe(true);
});
it('ignores unrelated database errors', () => {
expect(isDuplicateUsernameError({
message: 'UNIQUE constraint failed: servers.id'
})).toBe(false);
expect(isDuplicateUsernameError(new Error('connection lost'))).toBe(false);
expect(isDuplicateUsernameError(null)).toBe(false);
});
});

View File

@@ -0,0 +1,11 @@
export function isDuplicateUsernameError(error: unknown): boolean {
if (!error || typeof error !== 'object') {
return false;
}
const message = 'message' in error && typeof error.message === 'string'
? error.message
: '';
return message.includes('UNIQUE constraint failed: users.username');
}

View File

@@ -10,6 +10,7 @@ import {
import { hashPasswordForStorage, verifyPassword } from '../services/password-auth.service';
import { issueSessionToken, revokeSessionToken } from '../services/session-auth.service';
import { getAuthenticatedUserId, requireAuth } from '../middleware/require-auth';
import { isDuplicateUsernameError } from './user-registration.rules';
const router = Router();
@@ -46,7 +47,16 @@ router.post('/register', async (req, res) => {
createdAt: Date.now()
};
await registerUser(user);
try {
await registerUser(user);
} catch (error) {
if (isDuplicateUsernameError(error)) {
return res.status(409).json({ error: 'Username taken' });
}
throw error;
}
const session = await issueSessionToken(user.id);
res.status(201).json(buildAuthResponse(user, session.token, session.expiresAt));