From 5b6313f16f508882a0ea67716b7dbaa1c6967f04 Mon Sep 17 00:00:00 2001 From: dujinkim Date: Mon, 30 Jun 2025 08:28:13 +0000 Subject: (대표님) 20250630 16시 - 유저 도메인별 라우터 분리와 보안성검토 대응 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- lib/users/access-control/users-table.tsx | 166 +++++++++++++++++++++++++++++++ 1 file changed, 166 insertions(+) create mode 100644 lib/users/access-control/users-table.tsx (limited to 'lib/users/access-control/users-table.tsx') diff --git a/lib/users/access-control/users-table.tsx b/lib/users/access-control/users-table.tsx new file mode 100644 index 00000000..50ce4dee --- /dev/null +++ b/lib/users/access-control/users-table.tsx @@ -0,0 +1,166 @@ +"use client" + +import * as React from "react" +import { User} from "@/db/schema/users" +import type { + DataTableAdvancedFilterField, + DataTableFilterField, + DataTableRowAction, +} from "@/types/table" + +import { useDataTable } from "@/hooks/use-data-table" +import { DataTable } from "@/components/data-table/data-table" +import { DataTableAdvancedToolbar } from "@/components/data-table/data-table-advanced-toolbar" +import { DataTableToolbar } from "@/components/data-table/data-table-toolbar" + +import { getUsersNotPartners } from "@/lib/users/service"; +import { getColumns } from "./users-table-columns" +import { UsersTableToolbarActions } from "./users-table-toolbar-actions" +import { DomainStatsCards } from "./domain-stats-cards" + +interface UsersTableProps { + promises: Promise< + [ + Awaited>, + ] + > +} + +export function UserAccessControlTable({ promises }: UsersTableProps) { + const [{ data, pageCount }] = React.use(promises) + const [currentDomainFilter, setCurrentDomainFilter] = React.useState(null) + + const columns = React.useMemo(() => getColumns(), []) + + // 도메인 필터에 따른 데이터 필터링 + const filteredData = React.useMemo(() => { + if (!currentDomainFilter) { + return data // 필터가 없으면 전체 데이터 + } + return data.filter(user => user.domain === currentDomainFilter) + }, [data, currentDomainFilter]) + + // 필터링된 데이터의 페이지 수 재계산 + const filteredPageCount = React.useMemo(() => { + if (!currentDomainFilter) { + return pageCount // 필터가 없으면 원본 페이지 수 + } + // 필터링된 데이터는 페이지 수를 1로 설정 (클라이언트 필터링이므로) + return 1 + }, [pageCount, currentDomainFilter]) + + /** + * Advanced filter fields for the data table. + */ + const advancedFilterFields: DataTableAdvancedFilterField[] = [ + { + id: "name", + label: "사용자명", + type: "text", + }, + { + id: "email", + label: "이메일", + type: "text", + }, + { + id: "deptName", + label: "부서", + type: "text", + }, + { + id: "domain", + label: "도메인", + type: "multi-select", + options: [ + { label: "🟡 승인 대기", value: "pending" }, + { label: "🔵 전체 시스템", value: "evcp" }, + { label: "🟢 구매관리팀", value: "procurement" }, + { label: "🟣 기술영업팀", value: "sales" }, + { label: "🟠 설계관리팀", value: "engineering" }, + { label: "🟦 협력업체", value: "partners" }, + ], + }, + { + id: "createdAt", + label: "생성일", + type: "date", + }, + ] + + const { table } = useDataTable({ + data: filteredData, // 필터링된 데이터 사용 + columns, + pageCount: filteredPageCount, // 필터링된 페이지 수 사용 + enablePinning: true, + enableAdvancedFilter: true, + initialState: { + sorting: [{ id: "createdAt", desc: true }], + columnPinning: { right: ["actions"] }, + }, + getRowId: (originalRow) => `${originalRow.id}`, + shallow: false, + clearOnDefault: true, + }) + + // 도메인 필터 핸들러 (단순화) + const handleDomainFilter = React.useCallback((domain: string | null) => { + setCurrentDomainFilter(domain) + }, []) + + return ( +
+ {/* 도메인 통계 카드 */} + + + {/* 현재 필터 상태 표시 */} + {/* {currentDomainFilter && ( +
+
+ + 필터 적용됨: + + + {(() => { + const domainLabels = { + pending: "🟡 승인 대기", + evcp: "🔵 전체 시스템", + procurement: "🟢 구매관리팀", + sales: "🟣 기술영업팀", + engineering: "🟠 설계관리팀", + partners: "🟦 협력업체" + } + return domainLabels[currentDomainFilter as keyof typeof domainLabels] || currentDomainFilter + })()} + +
+
+ + {filteredData.length}명 표시 + + +
+
+ )} */} + + {/* 데이터 테이블 */} + + + + + +
+ ) +} \ No newline at end of file -- cgit v1.2.3