"use client"; import { useEffect, useState } from "react"; import { Table, TextField, SelectField, useToast } from "@nexarch/shl"; import type { TableColumn } from "@nexarch/shl"; import { ApiError, Assignment, Role, RoleInfo, assignRole, fetchRoleHistory, fetchRoles, } from "../../lib/api"; export default function RolesPage() { const { push } = useToast(); const [roles, setRoles] = useState(null); const [loadError, setLoadError] = useState(null); const [targetUserId, setTargetUserId] = useState(""); const [targetRole, setTargetRole] = useState("user"); const [assignError, setAssignError] = useState(null); const [submitting, setSubmitting] = useState(false); const [historyUserId, setHistoryUserId] = useState(""); const [history, setHistory] = useState(null); useEffect(() => { fetchRoles() .then(setRoles) .catch(() => setLoadError("Rollen konnten nicht geladen werden. Sind Sie als Tenant-Admin angemeldet?")); }, []); async function onAssign(event: React.FormEvent) { event.preventDefault(); setAssignError(null); setSubmitting(true); try { await assignRole(targetUserId, targetRole); push("Rolle zugewiesen.", "success"); } catch (err) { // Akzeptanzkriterium 2: die Backend-Meldung bei Selbst-Eskalation wird // unveraendert angezeigt, keine eigene Interpretation im Frontend. setAssignError(err instanceof ApiError ? err.message : "Rolle konnte nicht zugewiesen werden."); } finally { setSubmitting(false); } } async function onLoadHistory(event: React.FormEvent) { event.preventDefault(); try { setHistory(await fetchRoleHistory(historyUserId)); } catch { setHistory([]); } } const historyColumns: TableColumn[] = [ { key: "role", header: "Rolle", render: (a) => a.Role }, { key: "grantedBy", header: "Vergeben von", render: (a) => a.GrantedBy }, ]; if (loadError) { return (

{loadError}

); } return (

Rollen & Rechte

Rollen und Grundrechte

{roles?.map((r) => (
{roleLabel(r.role)}
    {r.permissions.map((p) => (
  • {p}
  • ))}
))}

Rolle zuweisen

setTargetUserId(e.target.value)} /> setTargetRole(e.target.value as Role)}> {assignError && (

{assignError}

)}

Nachvollziehbarkeit (Audit-Verlauf)

Zeigt jede Rollenzuweisung eines Benutzers chronologisch — wer wann welche Rolle vergeben hat.

setHistoryUserId(e.target.value)} /> {history && ( `${a.UserID}-${a.Role}-${a.GrantedBy}`} caption="Rollenzuweisungs-Verlauf" /> )} ); } function roleLabel(role: Role): string { return role === "tenant_admin" ? "Tenant-Admin" : "Benutzer"; }