diff --git a/api/src/server.ts b/api/src/server.ts index 5c61684..15fd15d 100644 --- a/api/src/server.ts +++ b/api/src/server.ts @@ -888,7 +888,11 @@ app.post( authRateLimit, async (req, reply) => { const parsed = RegisterBody.safeParse(req.body); - if (!parsed.success) return reply.code(400).send({ ok: false, message: "Invalid payload" }); + if (!parsed.success) { + const firstIssue = parsed.error.issues[0]; + const message = firstIssue?.message || "Invalid payload"; + return reply.code(400).send({ ok: false, message }); + } const { email, password } = parsed.data; const normalizedEmail = normalizeEmail(email); const existing = await app.prisma.user.findUnique({ diff --git a/web/src/pages/RegisterPage.tsx b/web/src/pages/RegisterPage.tsx index 01efc01..2610712 100644 --- a/web/src/pages/RegisterPage.tsx +++ b/web/src/pages/RegisterPage.tsx @@ -37,8 +37,13 @@ export default function RegisterPage() { const passwordError = (touched.password || submitted) && !password ? "Password is required." - : (touched.password || submitted) && password.length < 8 - ? "Password must be at least 8 characters." + : (touched.password || submitted) && + (password.length < 12 || + !/[a-z]/.test(password) || + !/[A-Z]/.test(password) || + !/\d/.test(password) || + !/[^A-Za-z0-9]/.test(password)) + ? "Use 12+ chars with upper, lower, number, and symbol." : ""; const confirmError = (touched.confirmPassword || submitted) && !confirmPassword @@ -87,7 +92,7 @@ export default function RegisterPage() { status === 409 ? "That email is already registered. Try signing in." : status === 400 - ? "Enter a valid email and password." + ? (err instanceof Error ? err.message : "Enter a valid email and password.") : err instanceof Error ? err.message : "Unable to register. Try again."; @@ -134,11 +139,16 @@ export default function RegisterPage() { onBlur={() => setTouched((prev) => ({ ...prev, password: true }))} autoComplete="new-password" required - minLength={8} + minLength={12} /> {passwordError && ( {passwordError} )} + {!passwordError && ( + + Must be 12+ chars and include uppercase, lowercase, number, and symbol. + + )}