import { useState } from 'react'; import { Link, useNavigate } from 'react-router-dom'; import { useTranslation } from 'react-i18next'; import { register, initiateGoogleLogin } from '../services/authService'; import { useAuthStore } from '../store/useAuthStore'; import { useLocalizedHref } from '../i18n/useLocalizedNavigate'; import { RESERVED_USERNAMES } from '../utils/reservedUsernames'; import { useSEO } from '../utils/useSEO'; import { trackSignUp } from '../utils/analytics'; export const RegisterPage: React.FC = () => { const { t } = useTranslation(); const localize = useLocalizedHref(); useSEO({ title: 'Create Account — Velxio', description: 'Create a free Velxio account to save your Arduino projects and share simulations.', url: 'https://velxio.dev/register', noindex: true, }); const navigate = useNavigate(); const setUser = useAuthStore((s) => s.setUser); const [username, setUsername] = useState(''); const [email, setEmail] = useState(''); const [password, setPassword] = useState(''); const [error, setError] = useState(''); const [loading, setLoading] = useState(false); const validateUsername = (name: string): string | null => { const lower = name.toLowerCase(); if (RESERVED_USERNAMES.has(lower)) return t('auth.register.errors.reserved'); if (!/^[a-z0-9_-]{3,30}$/.test(lower)) return t('auth.register.errors.usernameRules'); return null; }; const handleSubmit = async (e: React.FormEvent) => { e.preventDefault(); setError(''); const usernameErr = validateUsername(username); if (usernameErr) { setError(usernameErr); return; } if (password.length < 8) { setError(t('auth.register.errors.passwordTooShort')); return; } setLoading(true); try { const user = await register(username.toLowerCase(), email, password); trackSignUp('email'); setUser(user); navigate(localize('/editor')); } catch (err: any) { setError(err?.response?.data?.detail || t('auth.register.errors.failed')); } finally { setLoading(false); } }; return (
{t('auth.register.subtitle')}
{error &&{t('auth.register.haveAccount')}{' '} {t('header.auth.signIn')}