import { AlertCircle, CheckCircle, Shield, UserPlus } from "lucide-react"; import { useId, useState } from "react"; import { useNavigate } from "react-router-dom"; import { useAuth } from "../contexts/AuthContext"; import { isCorsError } from "../utils/api"; const FirstTimeAdminSetup = () => { const { login, setAuthState } = useAuth(); const navigate = useNavigate(); const firstNameId = useId(); const lastNameId = useId(); const usernameId = useId(); const emailId = useId(); const passwordId = useId(); const confirmPasswordId = useId(); const [formData, setFormData] = useState({ username: "", email: "", password: "", confirmPassword: "", firstName: "", lastName: "", }); const [isLoading, setIsLoading] = useState(false); const [error, setError] = useState(""); const [success, setSuccess] = useState(false); const handleInputChange = (e) => { const { name, value } = e.target; setFormData((prev) => ({ ...prev, [name]: value, })); // Clear error when user starts typing if (error) setError(""); }; const validateForm = () => { if (!formData.firstName.trim()) { setError("First name is required"); return false; } if (!formData.lastName.trim()) { setError("Last name is required"); return false; } if (!formData.username.trim()) { setError("Username is required"); return false; } if (!formData.email.trim()) { setError("Email address is required"); return false; } // Enhanced email validation const emailRegex = /^[^\s@]+@[^\s@]+\.[^\s@]+$/; if (!emailRegex.test(formData.email.trim())) { setError("Please enter a valid email address (e.g., user@example.com)"); return false; } if (formData.password.length < 8) { setError("Password must be at least 8 characters for security"); return false; } if (formData.password !== formData.confirmPassword) { setError("Passwords do not match"); return false; } return true; }; const handleSubmit = async (e) => { e.preventDefault(); if (!validateForm()) return; setIsLoading(true); setError(""); try { const response = await fetch("/api/v1/auth/setup-admin", { method: "POST", headers: { "Content-Type": "application/json", }, body: JSON.stringify({ username: formData.username.trim(), email: formData.email.trim(), password: formData.password, firstName: formData.firstName.trim(), lastName: formData.lastName.trim(), }), }); const data = await response.json(); if (response.ok) { setSuccess(true); // If the response includes a token, use it to automatically log in if (data.token && data.user) { // Set the authentication state immediately setAuthState(data.token, data.user); // Navigate to dashboard after successful setup setTimeout(() => { navigate("/", { replace: true }); }, 100); // Small delay to ensure auth state is set } else { // Fallback to manual login if no token provided setTimeout(async () => { try { await login(formData.username.trim(), formData.password); } catch (error) { console.error("Auto-login failed:", error); setError( "Account created but auto-login failed. Please login manually.", ); setSuccess(false); } }, 2000); } } else { // Handle HTTP error responses (like 500 CORS errors) console.log("HTTP error response:", response.status, data); // Check if this is a CORS error based on the response data if ( data.message?.includes("Not allowed by CORS") || data.message?.includes("CORS") || data.error?.includes("CORS") ) { setError( "CORS_ORIGIN mismatch - please set your URL in your environment variable", ); } else { setError(data.error || "Failed to create admin user"); } } } catch (error) { console.error("Setup error:", error); // Check for CORS/network errors first if (isCorsError(error)) { setError( "CORS_ORIGIN mismatch - please set your URL in your environment variable", ); } else if ( error.name === "TypeError" && error.message?.includes("Failed to fetch") ) { setError( "CORS_ORIGIN mismatch - please set your URL in your environment variable", ); } else { setError("Network error. Please try again."); } } finally { setIsLoading(false); } }; if (success) { return (
Your admin account has been successfully created and you are now logged in. Redirecting to the dashboard...
Let's set up your admin account to get started
Admin Privileges
This account will have full administrative access to manage users, hosts, packages, and system settings.