From 8ad07c49d576cb30c46f3faa0bb0a83ffd2aebea Mon Sep 17 00:00:00 2001 From: Matthias Mair <code@mjmair.com> Date: Thu, 9 Jan 2025 00:52:14 +0100 Subject: [PATCH] re-implement registrations --- .../components/forms/AuthenticationForm.tsx | 47 ++++++++++++++----- src/frontend/src/enums/ApiEndpoints.tsx | 2 +- src/frontend/src/functions/auth.tsx | 15 +++--- 3 files changed, 45 insertions(+), 19 deletions(-) diff --git a/src/frontend/src/components/forms/AuthenticationForm.tsx b/src/frontend/src/components/forms/AuthenticationForm.tsx index 0335b76943..e8e432c50f 100644 --- a/src/frontend/src/components/forms/AuthenticationForm.tsx +++ b/src/frontend/src/components/forms/AuthenticationForm.tsx @@ -21,6 +21,7 @@ import { ApiEndpoints } from '../../enums/ApiEndpoints'; import { doBasicLogin, doSimpleLogin, + ensureCsrf, followRedirect } from '../../functions/auth'; import { showLoginNotification } from '../../functions/notifications'; @@ -196,7 +197,12 @@ export function AuthenticationForm() { export function RegistrationForm() { const registrationForm = useForm({ - initialValues: { username: '', email: '', password1: '', password2: '' } + initialValues: { + username: '', + email: '', + password: '', + password2: '' as string | undefined + } }); const navigate = useNavigate(); const [auth_settings, registration_enabled, sso_registration] = @@ -207,14 +213,26 @@ export function RegistrationForm() { ]); const [isRegistering, setIsRegistering] = useState<boolean>(false); - function handleRegistration() { + async function handleRegistration() { + // check if passwords match + if ( + registrationForm.values.password !== registrationForm.values.password2 + ) { + registrationForm.setFieldError('password2', t`Passwords do not match`); + return; + } setIsRegistering(true); + + // remove password2 from the request + const { password2, ...vals } = registrationForm.values; + await ensureCsrf(); + api - .post(apiUrl(ApiEndpoints.user_register), registrationForm.values, { + .post(apiUrl(ApiEndpoints.user_register), vals, { headers: { Authorization: '' } }) .then((ret) => { - if (ret?.status === 204 || ret?.status === 201) { + if (ret?.status === 200) { setIsRegistering(false); showLoginNotification({ title: t`Registration successful`, @@ -226,16 +244,23 @@ export function RegistrationForm() { .catch((err) => { if (err.response?.status === 400) { setIsRegistering(false); - for (const [key, value] of Object.entries(err.response.data)) { - registrationForm.setFieldError(key, value as string); + + // collect all errors per field + const errors: { [key: string]: string[] } = {}; + for (const val of err.response.data.errors) { + if (!errors[val.param]) { + errors[val.param] = []; + } + errors[val.param].push(val.message); } - let err_msg = ''; - if (err.response?.data?.non_field_errors) { - err_msg = err.response.data.non_field_errors; + + for (const key in errors) { + registrationForm.setFieldError(key, errors[key]); } + showLoginNotification({ title: t`Input error`, - message: t`Check your input and try again. ` + err_msg, + message: t`Check your input and try again. `, success: false }); } @@ -268,7 +293,7 @@ export function RegistrationForm() { label={t`Password`} aria-label='register-password' placeholder={t`Your password`} - {...registrationForm.getInputProps('password1')} + {...registrationForm.getInputProps('password')} /> <PasswordInput required diff --git a/src/frontend/src/enums/ApiEndpoints.tsx b/src/frontend/src/enums/ApiEndpoints.tsx index c25e8d28db..1cedc5bde2 100644 --- a/src/frontend/src/enums/ApiEndpoints.tsx +++ b/src/frontend/src/enums/ApiEndpoints.tsx @@ -23,7 +23,7 @@ export enum ApiEndpoints { user_login = 'auth/v1/auth/login', user_login_mfa = 'auth/v1/auth/2fa/authenticate', user_logout = 'auth/v1/auth/session', - user_register = 'auth/registration/', // TODO change + user_register = 'auth/v1/auth/signup', user_mfa = 'auth/v1/account/authenticators', user_emails = 'auth/v1/account/email', login_provider_redirect = 'auth/v1/auth/provider/redirect', diff --git a/src/frontend/src/functions/auth.tsx b/src/frontend/src/functions/auth.tsx index 09bdf49f60..56c24abf34 100644 --- a/src/frontend/src/functions/auth.tsx +++ b/src/frontend/src/functions/auth.tsx @@ -72,16 +72,10 @@ export const doBasicLogin = async ( } clearCsrfCookie(); - const cookie = getCsrfCookie(); + await ensureCsrf(); const login_url = apiUrl(ApiEndpoints.user_login); - if (cookie == undefined) { - await api.get(apiUrl(ApiEndpoints.user_token)).catch(() => { - // his is to be expected - }); - } - let loginDone = false; let success = false; @@ -169,6 +163,13 @@ export const doSimpleLogin = async (email: string) => { return mail; }; +export async function ensureCsrf() { + const cookie = getCsrfCookie(); + if (cookie == undefined) { + await api.get(apiUrl(ApiEndpoints.user_token)).catch(() => {}); + } +} + export function handleReset( navigate: NavigateFunction, values: { email: string }