import React, { useState, useRef } from 'react'; import { useAuth } from '~/hooks/useAuth'; import type { RegisterResponse } from '~/routes/api.auth.register'; import { uploadToOSS } from '~/utils/uploadToOSS'; export function Register() { const [phone, setPhone] = useState(''); const [password, setPassword] = useState(''); const [confirmPassword, setConfirmPassword] = useState(''); const [nickname, setNickname] = useState(''); const [avatar, setAvatar] = useState(null); const [avatarPreview, setAvatarPreview] = useState(null); const [error, setError] = useState(null); const [isLoading, setIsLoading] = useState(false); const fileInputRef = useRef(null); const { login } = useAuth(); const handleAvatarChange = (e: React.ChangeEvent) => { const file = e.target.files?.[0]; if (file) { setAvatar(file); const reader = new FileReader(); reader.onloadend = () => { setAvatarPreview(reader.result as string); }; reader.readAsDataURL(file); } }; const handleSubmit = async (e: React.FormEvent) => { e.preventDefault(); setError(null); setIsLoading(true); if (password !== confirmPassword) { setError('两次输入的密码不一致'); setIsLoading(false); return; } if (!avatar) { setError('请上传头像'); setIsLoading(false); return; } try { const avatarUrl = await uploadToOSS(avatar); const registerResponse = await fetch('/api/auth/register', { method: 'POST', headers: { 'Content-Type': 'application/json', }, body: JSON.stringify({ phone, password, nickname, avatarUrl, }), }); const data = await registerResponse.json() as RegisterResponse; if (registerResponse.ok && data.token && data.user) { login(data.token, data.user); // 登录成功后,直接显示用户信息,不跳转 } else { setError(data.error || '注册失败,请稍后再试'); } } catch (error) { console.error('Registration failed:', error); setError('注册失败,请稍后再试'); } finally { setIsLoading(false); } }; return (
{error && (
{error}
)}
setPhone(e.target.value)} required className="mt-1 block w-full px-3 py-2 bg-bolt-elements-background-depth-1 border border-bolt-elements-borderColor rounded-md shadow-sm focus:outline-none focus:ring-bolt-elements-button-primary-background focus:border-bolt-elements-button-primary-background" />
setNickname(e.target.value)} required className="mt-1 block w-full px-3 py-2 bg-bolt-elements-background-depth-1 border border-bolt-elements-borderColor rounded-md shadow-sm focus:outline-none focus:ring-bolt-elements-button-primary-background focus:border-bolt-elements-button-primary-background" />
{avatarPreview ? ( Avatar preview ) : ( No image )}
setPassword(e.target.value)} required className="mt-1 block w-full px-3 py-2 bg-bolt-elements-background-depth-1 border border-bolt-elements-borderColor rounded-md shadow-sm focus:outline-none focus:ring-bolt-elements-button-primary-background focus:border-bolt-elements-button-primary-background" />
setConfirmPassword(e.target.value)} required className="mt-1 block w-full px-3 py-2 bg-bolt-elements-background-depth-1 border border-bolt-elements-borderColor rounded-md shadow-sm focus:outline-none focus:ring-bolt-elements-button-primary-background focus:border-bolt-elements-button-primary-background" />
); }