"use client" import {useEffect, useState} from "react" import {Button} from "@/components/ui/button" import {Dialog, DialogContent, DialogDescription, DialogHeader, DialogTitle} from "@/components/ui/dialog" import {Input} from "@/components/ui/input" import {Label} from "@/components/ui/label" import {Switch} from "@/components/ui/switch" import {useAdminUsers} from "@/contexts/admin-users-context" import {useAuth} from "@/components/providers/auth-provider" import type {AdminUser} from "@/lib/services/admin" import { AlertDialog, AlertDialogAction, AlertDialogCancel, AlertDialogContent, AlertDialogDescription, AlertDialogFooter, AlertDialogHeader, AlertDialogTitle } from "@/components/ui/alert-dialog" import {Loader2} from "lucide-react" interface EditUserForm { nickname: string email: string is_admin: boolean password?: string } export function EditUserModal({ isOpen, onClose, user, }: { isOpen: boolean onClose: () => void user: AdminUser | null }) { const { updateUser, deleteUser, getUserDetail } = useAdminUsers() const { user: currentUser } = useAuth() const isSelf = currentUser && user && currentUser.id.toString() === user.id.toString() const [form, setForm] = useState({ nickname: "", email: "", is_admin: false, password: "", }) const [saving, setSaving] = useState(false) const [errors, setErrors] = useState>({}) const [showDeleteConfirm, setShowDeleteConfirm] = useState(false) useEffect(() => { let active = true if (isOpen && user) { setForm({ nickname: user.nickname || "", email: user.email || "", is_admin: user.is_admin || false, password: "", }) setErrors({}) getUserDetail(user.id) .then((detail) => { if (active && detail) { setForm({ nickname: detail.nickname || "", email: detail.email || "", is_admin: detail.is_admin || false, password: "", }) } }) .catch(() => { // ignore fetching error }) } else { setSaving(false) } return () => { active = false } }, [isOpen, user, getUserDetail]) const validate = () => { const newErrors: Record = {} if (!form.email.trim()) { newErrors.email = "邮箱不能为空" } else if (!/^[^\s@]+@[^\s@]+\.[^\s@]+$/.test(form.email.trim())) { newErrors.email = "邮箱格式不正确" } if (form.password && form.password.length < 8) { newErrors.password = "密码长度不能少于 8 位" } setErrors(newErrors) return Object.keys(newErrors).length === 0 } const handleSave = async (e: React.FormEvent) => { e.preventDefault() if (!user || !validate()) return setSaving(true) try { await updateUser(user.id, { nickname: form.nickname.trim() || undefined, email: form.email.trim(), is_admin: form.is_admin, password: form.password?.trim() || undefined, }) onClose() } catch { // Errors are handled by context toast notifications } finally { setSaving(false) } } const handleDelete = async () => { if (!user) return setSaving(true) try { await deleteUser(user) onClose() } catch { // Errors are handled by context toast notifications } finally { setSaving(false) setShowDeleteConfirm(false) } } if (!user) return null return ( <> !open && onClose()}> 编辑用户 修改用户档案、授予/撤销管理权限或重置其密码。
setForm((prev) => ({ ...prev, nickname: e.target.value }))} placeholder="请输入昵称" />
setForm((prev) => ({ ...prev, email: e.target.value }))} placeholder="请输入邮箱地址" /> {errors.email && (

{errors.email}

)}
setForm((prev) => ({ ...prev, password: e.target.value }))} placeholder="留空表示保持当前密码,输入则重置 (至少 8 位)" /> {errors.password && (

{errors.password}

)}
管理员权限
{isSelf ? "不能撤销当前登录用户的管理员权限。" : "开启后此账号将拥有后台管理权限。"}
{ setForm((prev) => ({ ...prev, is_admin: checked })) setSaving(true) try { await updateUser(user.id, { nickname: form.nickname.trim() || undefined, email: form.email.trim(), is_admin: checked, }) } catch { setForm((prev) => ({ ...prev, is_admin: !checked })) } finally { setSaving(false) } }} />
{!user.is_admin && ( )}
确认删除用户 确定要删除用户 {user.nickname || user.username} 吗?该操作会移除用户账号,删除后无法撤销。 取消 { e.preventDefault() handleDelete() }} disabled={saving} > {saving && } 确认删除 ) }