diff --git a/frontend/src/features/admin/AccessControl.tsx b/frontend/src/features/admin/AccessControl.tsx index 2b6d5f9..08fda37 100644 --- a/frontend/src/features/admin/AccessControl.tsx +++ b/frontend/src/features/admin/AccessControl.tsx @@ -2,6 +2,8 @@ import { useEffect, useState, useCallback, useMemo } from 'react'; import { useTranslation } from 'react-i18next'; import { Card, CardContent, CardHeader, CardTitle } from '@shared/components/ui/card'; import { Badge } from '@shared/components/ui/badge'; +import { Button } from '@shared/components/ui/button'; +import { PageContainer, PageHeader } from '@shared/components/layout'; import { DataTable, type DataColumn } from '@shared/components/common/DataTable'; import { Shield, Users, UserCheck, Key, Lock, FileText, Loader2, RefreshCw, UserCog, @@ -183,33 +185,36 @@ export function AccessControl() { ], []); return ( -
-
-
-

- - {t('accessControl.title')} -

-

{t('accessControl.desc')}

-
-
- {userStats && ( -
- - 활성 {userStats.active}명 - | - 잠금 {userStats.locked} - | - 총 {userStats.total} -
- )} - -
-
+ + + {userStats && ( +
+ + 활성 {userStats.active}명 + | + 잠금 {userStats.locked} + | + 총 {userStats.total} +
+ )} + + + } + /> {/* 탭 */}
@@ -354,7 +359,7 @@ export function AccessControl() { ]} />
)} -
+ ); } diff --git a/frontend/src/features/admin/AccessLogs.tsx b/frontend/src/features/admin/AccessLogs.tsx index 329417e..6e367c3 100644 --- a/frontend/src/features/admin/AccessLogs.tsx +++ b/frontend/src/features/admin/AccessLogs.tsx @@ -1,7 +1,9 @@ import { useEffect, useState, useCallback } from 'react'; -import { Loader2, RefreshCw } from 'lucide-react'; +import { Loader2, RefreshCw, Activity } from 'lucide-react'; import { Card, CardContent, CardHeader, CardTitle } from '@shared/components/ui/card'; import { Badge } from '@shared/components/ui/badge'; +import { Button } from '@shared/components/ui/button'; +import { PageContainer, PageHeader } from '@shared/components/layout'; import { fetchAccessLogs, fetchAccessStats, type AccessLog, type AccessStats } from '@/services/adminApi'; import { formatDateTime } from '@shared/utils/dateFormat'; import { getHttpStatusIntent } from '@shared/constants/httpStatusCodes'; @@ -32,16 +34,18 @@ export function AccessLogs() { useEffect(() => { load(); }, [load]); return ( -
-
-
-

접근 이력

-

AccessLogFilter가 모든 HTTP 요청 비동기 기록

-
- -
+ + }> + 새로고침 + + } + /> {stats && (
@@ -120,7 +124,7 @@ export function AccessLogs() { )} -
+
); } diff --git a/frontend/src/features/admin/AdminPanel.tsx b/frontend/src/features/admin/AdminPanel.tsx index 6a66e06..5761c36 100644 --- a/frontend/src/features/admin/AdminPanel.tsx +++ b/frontend/src/features/admin/AdminPanel.tsx @@ -1,6 +1,7 @@ import { useTranslation } from 'react-i18next'; import { Card, CardContent, CardHeader, CardTitle } from '@shared/components/ui/card'; -import { Settings, Server, HardDrive, Shield, Clock, Database } from 'lucide-react'; +import { PageContainer, PageHeader } from '@shared/components/layout'; +import { Settings, Server, Shield, Database } from 'lucide-react'; /* * 시스템 관리 — 서버 상태, 디스크, 보안 설정 등 인프라 관리 @@ -30,17 +31,13 @@ function UsageBar({ value }: { value: number }) { export function AdminPanel() { const { t } = useTranslation('admin'); return ( -
-
-

- - {t('adminPanel.title')} - - 데모 데이터 (백엔드 API 미구현) - -

-

{t('adminPanel.desc')}

-
+ + {/* 서버 상태 */}
@@ -89,6 +86,6 @@ export function AdminPanel() {
-
+ ); } diff --git a/frontend/src/features/admin/AuditLogs.tsx b/frontend/src/features/admin/AuditLogs.tsx index c427527..a0d1d59 100644 --- a/frontend/src/features/admin/AuditLogs.tsx +++ b/frontend/src/features/admin/AuditLogs.tsx @@ -1,7 +1,9 @@ import { useEffect, useState, useCallback } from 'react'; -import { Loader2, RefreshCw } from 'lucide-react'; +import { Loader2, RefreshCw, FileSearch } from 'lucide-react'; import { Card, CardContent, CardHeader, CardTitle } from '@shared/components/ui/card'; import { Badge } from '@shared/components/ui/badge'; +import { Button } from '@shared/components/ui/button'; +import { PageContainer, PageHeader } from '@shared/components/layout'; import { fetchAuditLogs, fetchAuditStats, type AuditLog, type AuditStats } from '@/services/adminApi'; import { formatDateTime } from '@shared/utils/dateFormat'; @@ -31,16 +33,18 @@ export function AuditLogs() { useEffect(() => { load(); }, [load]); return ( -
-
-
-

감사 로그

-

@Auditable AOP가 모든 운영자 의사결정 자동 기록

-
- -
+ + }> + 새로고침 + + } + /> {/* 통계 카드 */} {stats && ( @@ -115,7 +119,7 @@ export function AuditLogs() { )} -
+ ); } diff --git a/frontend/src/features/admin/DataHub.tsx b/frontend/src/features/admin/DataHub.tsx index 713376e..c6a8220 100644 --- a/frontend/src/features/admin/DataHub.tsx +++ b/frontend/src/features/admin/DataHub.tsx @@ -2,6 +2,8 @@ import { useState, useMemo } from 'react'; import { useTranslation } from 'react-i18next'; import { Card, CardContent, CardHeader, CardTitle } from '@shared/components/ui/card'; import { Badge } from '@shared/components/ui/badge'; +import { Button } from '@shared/components/ui/button'; +import { PageContainer, PageHeader } from '@shared/components/layout'; import { DataTable, type DataColumn } from '@shared/components/common/DataTable'; import { SaveButton } from '@shared/components/common/SaveButton'; import { getConnectionStatusHex } from '@shared/constants/connectionStatuses'; @@ -380,28 +382,19 @@ export function DataHub() { ); return ( -
- {/* 헤더 */} -
-
-

- - {t('dataHub.title')} - - 데모 데이터 (백엔드 API 미구현) - -

-

- {t('dataHub.desc')} -

-
-
- -
-
+ + } + /> {/* KPI */}
@@ -670,6 +663,6 @@ export function DataHub() {
)} -
+ ); } diff --git a/frontend/src/features/admin/LoginHistoryView.tsx b/frontend/src/features/admin/LoginHistoryView.tsx index 3d14500..0578536 100644 --- a/frontend/src/features/admin/LoginHistoryView.tsx +++ b/frontend/src/features/admin/LoginHistoryView.tsx @@ -1,7 +1,9 @@ import { useEffect, useState, useCallback } from 'react'; -import { Loader2, RefreshCw } from 'lucide-react'; +import { Loader2, RefreshCw, LogIn } from 'lucide-react'; import { Card, CardContent, CardHeader, CardTitle } from '@shared/components/ui/card'; import { Badge } from '@shared/components/ui/badge'; +import { Button } from '@shared/components/ui/button'; +import { PageContainer, PageHeader } from '@shared/components/layout'; import { fetchLoginHistory, fetchLoginStats, type LoginHistory, type LoginStats } from '@/services/adminApi'; import { formatDateTime, formatDate } from '@shared/utils/dateFormat'; import { getLoginResultIntent, getLoginResultLabel } from '@shared/constants/loginResultStatuses'; @@ -36,16 +38,18 @@ export function LoginHistoryView() { useEffect(() => { load(); }, [load]); return ( -
-
-
-

로그인 이력

-

성공/실패 로그인 시도 기록 (5회 실패 시 자동 잠금)

-
- -
+ + }> + 새로고침 + + } + /> {/* 통계 카드 */} {stats && ( @@ -133,7 +137,7 @@ export function LoginHistoryView() { )} -
+ ); } diff --git a/frontend/src/features/admin/NoticeManagement.tsx b/frontend/src/features/admin/NoticeManagement.tsx index 2b15ea5..d3c8e7a 100644 --- a/frontend/src/features/admin/NoticeManagement.tsx +++ b/frontend/src/features/admin/NoticeManagement.tsx @@ -2,6 +2,8 @@ import { useState } from 'react'; import { useTranslation } from 'react-i18next'; import { Card, CardContent, CardHeader, CardTitle } from '@shared/components/ui/card'; import { Badge } from '@shared/components/ui/badge'; +import { Button } from '@shared/components/ui/button'; +import { PageContainer, PageHeader } from '@shared/components/layout'; import { Bell, Plus, Edit2, Trash2, Eye, EyeOff, Calendar, Users, Megaphone, AlertTriangle, Info, Search, Filter, @@ -135,29 +137,19 @@ export function NoticeManagement() { const urgentCount = notices.filter((n) => n.type === 'urgent' && n.startDate <= now && n.endDate >= now).length; return ( -
- {/* 헤더 */} -
-
-

- - {t('notices.title')} - - 데모 데이터 (백엔드 API 미구현) - -

-

- {t('notices.desc')} -

-
- -
+ + }> + 새 알림 등록 + + } + /> {/* KPI — 가로 한 줄 */}
@@ -423,6 +415,6 @@ export function NoticeManagement() {
)} - + ); } diff --git a/frontend/src/features/admin/SystemConfig.tsx b/frontend/src/features/admin/SystemConfig.tsx index 9b55e59..1453e3c 100644 --- a/frontend/src/features/admin/SystemConfig.tsx +++ b/frontend/src/features/admin/SystemConfig.tsx @@ -2,6 +2,8 @@ import { useState, useMemo } from 'react'; import { useTranslation } from 'react-i18next'; import { Card, CardContent, CardHeader, CardTitle } from '@shared/components/ui/card'; import { Badge } from '@shared/components/ui/badge'; +import { Button } from '@shared/components/ui/button'; +import { PageContainer, PageHeader } from '@shared/components/layout'; import { Settings, Database, Search, ChevronDown, ChevronRight, Map, Fish, Anchor, Ship, Globe, BarChart3, Download, @@ -143,32 +145,24 @@ export function SystemConfig() { : []; return ( -
- {/* 헤더 */} -
-
-

- - {t('systemConfig.title')} - - 데모 데이터 (백엔드 API 미구현) - -

-

- {t('systemConfig.desc')} -

-
-
- - -
-
+ + + + + + } + /> {/* KPI 카드 */}
@@ -505,6 +499,6 @@ export function SystemConfig() { })}
)} -
+ ); }