diff options
| author | Fuwn <[email protected]> | 2026-01-24 13:09:50 +0000 |
|---|---|---|
| committer | Fuwn <[email protected]> | 2026-01-24 13:09:50 +0000 |
| commit | 396acf3bbbe00a192cb0ea0a9ccf91b1d8d2850b (patch) | |
| tree | b9df4ca6a70db45cfffbae6fdd7252e20fb8e93c /src/app/api/auth/login | |
| download | umami-396acf3bbbe00a192cb0ea0a9ccf91b1d8d2850b.tar.xz umami-396acf3bbbe00a192cb0ea0a9ccf91b1d8d2850b.zip | |
Created from https://vercel.com/new
Diffstat (limited to 'src/app/api/auth/login')
| -rw-r--r-- | src/app/api/auth/login/route.ts | 48 |
1 files changed, 48 insertions, 0 deletions
diff --git a/src/app/api/auth/login/route.ts b/src/app/api/auth/login/route.ts new file mode 100644 index 0000000..17ca2f7 --- /dev/null +++ b/src/app/api/auth/login/route.ts @@ -0,0 +1,48 @@ +import { z } from 'zod'; +import { saveAuth } from '@/lib/auth'; +import { ROLES } from '@/lib/constants'; +import { secret } from '@/lib/crypto'; +import { createSecureToken } from '@/lib/jwt'; +import { checkPassword } from '@/lib/password'; +import redis from '@/lib/redis'; +import { parseRequest } from '@/lib/request'; +import { json, unauthorized } from '@/lib/response'; +import { getAllUserTeams, getUserByUsername } from '@/queries/prisma'; + +export async function POST(request: Request) { + const schema = z.object({ + username: z.string(), + password: z.string(), + }); + + const { body, error } = await parseRequest(request, schema, { skipAuth: true }); + + if (error) { + return error(); + } + + const { username, password } = body; + + const user = await getUserByUsername(username, { includePassword: true }); + + if (!user || !checkPassword(password, user.password)) { + return unauthorized({ code: 'incorrect-username-password' }); + } + + const { id, role, createdAt } = user; + + let token: string; + + if (redis.enabled) { + token = await saveAuth({ userId: id, role }); + } else { + token = createSecureToken({ userId: user.id, role }, secret()); + } + + const teams = await getAllUserTeams(id); + + return json({ + token, + user: { id, username, role, createdAt, isAdmin: role === ROLES.admin, teams }, + }); +} |