fix: localadmin displayName 从数据库读取;Sidebar 权限驱动导航(userRole prop)

This commit is contained in:
aiyimickey 2026-07-02 11:25:44 +08:00
parent b5b59f1c3b
commit c876a69443
3 changed files with 9 additions and 9 deletions

View File

@ -24,12 +24,13 @@ export async function POST(request: NextRequest) {
// localadmin 密码验证(查询数据库存储的密码)
if (username === 'localadmin') {
const users = dbQuery<{ password_hash: string; role: string }>(`SELECT password_hash, role FROM users WHERE username = 'localadmin'`)
const users = dbQuery<{ password_hash: string; role: string; display_name: string | null }>(`SELECT password_hash, role, display_name FROM users WHERE username = 'localadmin'`)
if (users.length === 0) {
return NextResponse.json({ error: 'localadmin 未配置' }, { status: 401 })
}
const localadminUser = users[0]
// 与数据库存储的 bcrypt 哈希比较
if (!bcrypt.compareSync(password, users[0].password_hash)) {
if (!bcrypt.compareSync(password, localadminUser.password_hash)) {
writeAuditLog({ exec: dbExec }, {
username, action: 'login_failed', entityType: 'auth',
details: { method: 'localadmin', reason: 'wrong_password' },
@ -38,7 +39,9 @@ export async function POST(request: NextRequest) {
return NextResponse.json({ error: '密码错误' }, { status: 401 })
}
const token = signJwt({ secret: authConfig.jwtSecret, payload: { username: 'localadmin', role: 'admin', displayName: 'localadmin' } })
const displayName = localadminUser.display_name || 'localadmin'
const role = localadminUser.role || 'admin'
const token = signJwt({ secret: authConfig.jwtSecret, payload: { username: 'localadmin', role, displayName } })
writeAuditLog({ exec: dbExec }, {
username, action: 'login', entityType: 'auth',
@ -47,7 +50,7 @@ export async function POST(request: NextRequest) {
})
const response = NextResponse.json({
user: { username: 'localadmin', role: 'admin', displayName: 'localadmin' },
user: { username: 'localadmin', role, displayName },
})
response.cookies.set('tlyq_session', token, {
httpOnly: true, secure: false, sameSite: 'lax', path: '/', maxAge: 604800,

View File

@ -28,7 +28,7 @@ export default function ClientLayout({ children }: { children: React.ReactNode }
return (
<ThemeProvider>
<div className="min-h-screen bg-slate-50 dark:bg-slate-950">
<Sidebar />
<Sidebar userRole={user?.role} />
<TopBar user={user} />
<main className="ml-60 pt-14 min-h-screen">
<div className="p-6">{children}</div>

View File

@ -8,13 +8,10 @@ import { hasPermission } from '@/lib/permissions'
interface NavItem { label: string; href: string; icon: React.ComponentType<{ size?: number }>; permission?: string }
interface NavSection { title?: string; items: NavItem[] }
export default function Sidebar() {
export default function Sidebar({ userRole = 'viewer' }: { userRole?: string }) {
const pathname = usePathname()
const isActive = (href: string) => pathname === href || (href !== '/' && pathname.startsWith(href))
// 默认显示所有导航项(客户端权限在 API 层强制验证,此处仅 UI 过滤)
const userRole = 'admin' // TODO: 从 cookie 或 session 读取实际角色
const sections: NavSection[] = [
{
items: [