This commit is contained in:
2026-02-16 19:34:35 +00:00
commit 9ab0940ca4
784 changed files with 41710 additions and 0 deletions
+37
View File
@@ -0,0 +1,37 @@
import type { Handler } from 'hono';
import { officerdb, eq, Users } from 'officerdb';
import argon2 from 'argon2';
import { sign } from '@@/jwt';
import * as errors from '@@/custom-errors';
import { validatePassword } from './validate-password';
const { PUBLIC_BUILD_ENV } = process.env;
const isProduction = PUBLIC_BUILD_ENV === 'production' || PUBLIC_BUILD_ENV === 'staging';
export const changePasswordHandler: Handler = async function (ctx) {
const { password, newPassword } = ctx.get('body');
if (isProduction) validatePassword(newPassword);
const reqUser = ctx.get('user');
const dbUser = await officerdb.query.Users.findFirst({
where: eq(Users.id, reqUser.id),
columns: { password: true },
});
if (!dbUser) throw errors.UNAUTHORIZED();
const isCorrectOldPassword = await argon2.verify(dbUser.password!, password);
if (!isCorrectOldPassword) {
throw errors.createError(403, 'Incorrect old password');
}
const newPasswordHash = await argon2.hash(newPassword);
// Use floored seconds-to-ms so the token iat (also floored) is never behind
const passwordChangedAt = Math.floor(Date.now() / 1000) * 1000;
await officerdb.update(Users).set({ password: newPasswordHash, passwordChangedAt }).where(eq(Users.id, reqUser.id));
const { id, email, name, role } = reqUser;
const token = await sign({ id, email, name, role });
return ctx.json({ token });
};