Files
jiang13-bbs/frontend/app/admin/users/page.tsx
freefire 6da4309453 feat: 新增管理员用户管理功能与账号封禁体系
此提交完成了全站管理员后台核心功能开发:
1.  新增AdminUserService与管理接口,支持用户列表查询、角色变更与封禁解封
2.  重构认证链路,统一账号封禁错误码与处理逻辑
3.  新增全局强制下线机制,账号被封禁时自动弹出告知弹窗并清理登录态
4.  重构管理员后台路由与布局,统一权限校验逻辑
5.  优化通知轮询逻辑,页面切回前台时立即刷新未读计数
6.  合并原公告、外观管理页到统一后台面板
2026-09-15 02:52:26 +08:00

50 lines
1.7 KiB
TypeScript
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
import type { Metadata } from "next";
import { cookies } from "next/headers";
import { authCookieHeader } from "@/lib/cookies";
import { fetchAdminUsers, type AdminUsersResponse } from "@/lib/api";
import { getMeCached } from "@/lib/serverData";
import UsersAdmin, { type UserFilter } from "./UsersAdmin";
export const metadata: Metadata = {
title: "用户管理",
};
interface UsersPageProps {
searchParams: Promise<{ q?: string; filter?: string; page?: string }>;
}
// 筛选项映射为后端查询参数:管理员走 role,封禁走 status,其余不过滤
function filterToQuery(filter: UserFilter): { role?: string; status?: string } {
if (filter === "admin") return { role: "admin" };
if (filter === "banned") return { status: "banned" };
return {};
}
// 管理员鉴权由 app/admin/layout.tsx 统一承担;列表首屏 SSR 直出,F5 无骨架闪动
export default async function AdminUsersPage({ searchParams }: UsersPageProps) {
const sp = await searchParams;
const q = sp.q?.trim() || "";
const filter: UserFilter = sp.filter === "admin" || sp.filter === "banned" ? sp.filter : "all";
const page = Math.max(1, parseInt(sp.page || "1", 10) || 1);
const cookie = authCookieHeader(await cookies());
const me = await getMeCached(cookie || undefined);
let initial: AdminUsersResponse | null = null;
let initError = "";
try {
initial = await fetchAdminUsers({ page, q, ...filterToQuery(filter) }, cookie || undefined);
} catch (e) {
initError = e instanceof Error ? e.message : "获取用户列表失败";
}
return (
<UsersAdmin
initial={initial}
initError={initError}
initialQuery={{ q, filter, page }}
currentUserId={me.user?.id ?? 0}
/>
);
}