forked from baron/baron-sso
adminfront 및 백엔드: ReBAC 기반 각 탭별 읽기/쓰기 권한 제어 구현
This commit is contained in:
@@ -29,6 +29,7 @@ type DomainTagInputProps = {
|
||||
confirmedConflicts?: string[];
|
||||
onConfirmedConflictsChange?: (domains: string[]) => void;
|
||||
placeholder?: string;
|
||||
disabled?: boolean;
|
||||
};
|
||||
|
||||
export function DomainTagInput({
|
||||
@@ -40,6 +41,7 @@ export function DomainTagInput({
|
||||
confirmedConflicts = [],
|
||||
onConfirmedConflictsChange,
|
||||
placeholder,
|
||||
disabled = false,
|
||||
}: DomainTagInputProps) {
|
||||
const [input, setInput] = useState("");
|
||||
const [pendingConflict, setPendingConflict] = useState<DomainConflict | null>(
|
||||
@@ -107,14 +109,16 @@ export function DomainTagInput({
|
||||
className="gap-1 rounded-md"
|
||||
>
|
||||
<span>{domain}</span>
|
||||
<button
|
||||
type="button"
|
||||
className="inline-flex h-4 w-4 items-center justify-center rounded-sm hover:bg-background/60"
|
||||
onClick={() => removeDomain(domain)}
|
||||
aria-label={t("ui.common.remove", "삭제")}
|
||||
>
|
||||
<X size={12} />
|
||||
</button>
|
||||
{!disabled && (
|
||||
<button
|
||||
type="button"
|
||||
className="inline-flex h-4 w-4 items-center justify-center rounded-sm hover:bg-background/60"
|
||||
onClick={() => removeDomain(domain)}
|
||||
aria-label={t("ui.common.remove", "삭제")}
|
||||
>
|
||||
<X size={12} />
|
||||
</button>
|
||||
)}
|
||||
</Badge>
|
||||
))}
|
||||
<Input
|
||||
@@ -133,6 +137,7 @@ export function DomainTagInput({
|
||||
tokenizeInput();
|
||||
}
|
||||
}}
|
||||
disabled={disabled}
|
||||
className="h-7 min-w-[180px] flex-1 border-0 px-0 py-0 shadow-none focus-visible:ring-0"
|
||||
placeholder={value.length === 0 ? placeholder : undefined}
|
||||
/>
|
||||
|
||||
@@ -35,6 +35,7 @@ type ParentTenantSelectorProps = {
|
||||
localTenantFilter?: (tenant: TenantSummary) => boolean;
|
||||
compact?: boolean;
|
||||
controlTestId?: string;
|
||||
disabled?: boolean;
|
||||
};
|
||||
|
||||
export function ParentTenantSelector({
|
||||
@@ -53,6 +54,7 @@ export function ParentTenantSelector({
|
||||
localTenantFilter,
|
||||
compact = false,
|
||||
controlTestId,
|
||||
disabled = false,
|
||||
}: ParentTenantSelectorProps) {
|
||||
const [pickerOpen, setPickerOpen] = useState(false);
|
||||
const [localPickerOpen, setLocalPickerOpen] = useState(false);
|
||||
@@ -112,6 +114,7 @@ export function ParentTenantSelector({
|
||||
variant="outline"
|
||||
size="sm"
|
||||
className={compact ? "h-8 shrink-0 px-2" : undefined}
|
||||
disabled={disabled}
|
||||
>
|
||||
<Building2 className="h-4 w-4" />
|
||||
{orgChartPickerLabel ??
|
||||
@@ -141,7 +144,7 @@ export function ParentTenantSelector({
|
||||
{localPickerLabel && (
|
||||
<Dialog open={localPickerOpen} onOpenChange={setLocalPickerOpen}>
|
||||
<DialogTrigger asChild>
|
||||
<Button type="button" variant="outline" size="sm">
|
||||
<Button type="button" variant="outline" size="sm" disabled={disabled}>
|
||||
<Building2 className="h-4 w-4" />
|
||||
{localPickerLabel}
|
||||
</Button>
|
||||
@@ -228,6 +231,7 @@ export function ParentTenantSelector({
|
||||
className={compact ? "h-7 w-7 shrink-0" : "h-8 w-8"}
|
||||
onClick={() => onChange("")}
|
||||
aria-label={noneLabel}
|
||||
disabled={disabled}
|
||||
>
|
||||
<X className="h-4 w-4" />
|
||||
</Button>
|
||||
|
||||
@@ -0,0 +1,26 @@
|
||||
import type React from "react";
|
||||
import { useTenantPermission } from "../hooks/useTenantPermission";
|
||||
|
||||
interface TenantPermissionGuardProps {
|
||||
tenantId: string;
|
||||
relation: "view" | "manage" | "manage_admins";
|
||||
fallback?: React.ReactNode;
|
||||
children: React.ReactNode;
|
||||
}
|
||||
|
||||
export function TenantPermissionGuard({
|
||||
tenantId,
|
||||
relation,
|
||||
fallback = null,
|
||||
children,
|
||||
}: TenantPermissionGuardProps) {
|
||||
const { hasPermission, isLoading } = useTenantPermission(tenantId);
|
||||
|
||||
if (isLoading) return null;
|
||||
|
||||
if (!hasPermission(relation)) {
|
||||
return <>{fallback}</>;
|
||||
}
|
||||
|
||||
return <>{children}</>;
|
||||
}
|
||||
Reference in New Issue
Block a user