- tsconfig.json strict mode (noImplicitAny, strictNullChecks, noUnused*) - Replace nodemon with tsx (watch + run TS directly) - Build script (tsc -> dist/) and typecheck script - Fastify decorator types in types/fastify.d.ts (prisma, openai, stripe, googleClient, auth helpers, ai helpers, request.user) - Typed route handlers with generic Body/Params - Strict null checks on Prisma results and env vars - Stripe plugin now optional (no-op if STRIPE_SECRET_KEY missing) - Delete dead utils/errors.js (empty) and utils/resend.js (contained a hardcoded Resend API key, unused) - Add @types/bcrypt, @types/nodemailer, typescript-eslint - ESLint upgraded to typescript-eslint flat config - deploy.sh: run prisma generate, migrate deploy, backend build Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
27 lines
787 B
TypeScript
27 lines
787 B
TypeScript
import fp from 'fastify-plugin';
|
|
import jwt from '@fastify/jwt';
|
|
import bcrypt from 'bcrypt';
|
|
import type { FastifyInstance, FastifyRequest, FastifyReply } from 'fastify';
|
|
|
|
const SALT_ROUNDS = 10;
|
|
|
|
export default fp(async function authPlugin(fastify: FastifyInstance) {
|
|
await fastify.register(jwt, {
|
|
secret: process.env.JWT_SECRET!,
|
|
});
|
|
|
|
fastify.decorate('authenticate', async function (request: FastifyRequest, reply: FastifyReply) {
|
|
try {
|
|
await request.jwtVerify();
|
|
} catch {
|
|
reply.code(401).send({ error: 'Non authentifié' });
|
|
}
|
|
});
|
|
|
|
fastify.decorate('hashPassword', (password: string) => bcrypt.hash(password, SALT_ROUNDS));
|
|
|
|
fastify.decorate('comparePassword', (password: string, hash: string) =>
|
|
bcrypt.compare(password, hash)
|
|
);
|
|
});
|