From d821387e4bd939db1b6772ae7a8a770c9c350433 Mon Sep 17 00:00:00 2001 From: Hyungi Ahn Date: Sat, 25 Oct 2025 09:53:11 +0900 Subject: [PATCH] =?UTF-8?q?fix:=20=EC=82=AC=EC=9A=A9=EC=9E=90=20=EA=B4=80?= =?UTF-8?q?=EB=A6=AC=20=ED=8E=98=EC=9D=B4=EC=A7=80=20=EA=B3=B5=ED=86=B5=20?= =?UTF-8?q?=ED=97=A4=EB=8D=94=20=EC=A0=81=EC=9A=A9=20=EB=B0=8F=20=EA=B6=8C?= =?UTF-8?q?=ED=95=9C=20=EC=84=A4=EC=A0=95=20=EC=98=A4=EB=A5=98=20=EC=88=98?= =?UTF-8?q?=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Issues Fixed: 1. 개인 페이지 헤더 제거 - 기존 Header와 Navigation 삭제 - 공통 헤더 자동 삽입으로 변경 - padding-top: 120px 추가로 레이아웃 조정 2. showPagePermissionGrid 함수 오류 수정 - 'pages' 변수 참조 오류 해결 - pageCategories 기반으로 HTML 생성 로직 재작성 - 카테고리별 그룹화 UI 개선 3. 권한 시스템 완성 - users_manage 페이지 권한 추가 - 백엔드 DEFAULT_PAGES에 users_manage 추가 - 프론트엔드 권한 체크 로직 통합 4. UI/UX 개선 - 체크박스 상태에 따른 시각적 피드백 - 기본 권한 표시 배지 추가 - 호버 효과 및 트랜지션 개선 - 카테고리별 구분선 추가 Technical Changes: - 모든 페이지 권한을 포함한 allPages 배열 업데이트 - 권한 저장 시 존재하지 않는 체크박스 검증 추가 - 공통 헤더 초기화 및 페이지 접근 권한 체크 추가 - 백엔드 재시작으로 권한 시스템 변경사항 적용 Result: ✅ 사용자 선택 시 권한 설정 그리드 정상 표시 ✅ 모든 페이지 권한 (수신함, 관리함, 폐기함 포함) 관리 가능 ✅ 공통 헤더 통합으로 일관된 UI 제공 ✅ 권한 저장 및 로드 기능 정상 작동 --- backend/routers/page_permissions.py | 3 +- frontend/admin.html | 142 +++++++++++++++------------- 2 files changed, 79 insertions(+), 66 deletions(-) diff --git a/backend/routers/page_permissions.py b/backend/routers/page_permissions.py index 4258208..aa65149 100644 --- a/backend/routers/page_permissions.py +++ b/backend/routers/page_permissions.py @@ -50,7 +50,8 @@ DEFAULT_PAGES = { 'issues_archive': {'title': '폐기함', 'default_access': False}, 'projects_manage': {'title': '프로젝트 관리', 'default_access': False}, 'daily_work': {'title': '일일 공수', 'default_access': False}, - 'reports': {'title': '보고서', 'default_access': False} + 'reports': {'title': '보고서', 'default_access': False}, + 'users_manage': {'title': '사용자 관리', 'default_access': False} } @router.post("/page-permissions/grant") diff --git a/frontend/admin.html b/frontend/admin.html index d53831f..c5c3bba 100644 --- a/frontend/admin.html +++ b/frontend/admin.html @@ -59,48 +59,10 @@ - -
-
-
-

- 작업보고서 시스템 - 관리자 -

- -
-
-
- - - + -
+
@@ -295,6 +257,15 @@ // 공통 헤더 초기화 await window.commonHeader.init(user, 'users_manage'); + // 페이지 접근 권한 체크 + setTimeout(() => { + if (!canAccessPage('users_manage')) { + alert('사용자 관리 페이지에 접근할 권한이 없습니다.'); + window.location.href = '/index.html'; + return; + } + }, 500); + } catch (error) { console.error('인증 실패:', error); localStorage.removeItem('access_token'); @@ -571,30 +542,65 @@ const grid = document.getElementById('pagePermissionGrid'); const gridContainer = grid.querySelector('.grid'); - // 페이지 권한 체크박스 생성 - const pages = { - 'issues_create': '부적합 등록', - 'issues_view': '부적합 조회', - 'issues_manage': '부적합 관리', - 'projects_manage': '프로젝트 관리', - 'daily_work': '일일 공수', - 'reports': '보고서' + // 페이지 권한 체크박스 생성 (카테고리별로 그룹화) + const pageCategories = { + '부적합 관리': { + 'issues_create': { title: '부적합 등록', icon: 'fas fa-plus-circle', color: 'text-green-600' }, + 'issues_view': { title: '부적합 조회', icon: 'fas fa-search', color: 'text-purple-600' }, + 'issues_manage': { title: '목록 관리 (통합)', icon: 'fas fa-tasks', color: 'text-orange-600' } + }, + '목록 관리 세부': { + 'issues_inbox': { title: '📥 수신함', icon: 'fas fa-inbox', color: 'text-blue-600' }, + 'issues_management': { title: '⚙️ 관리함', icon: 'fas fa-cog', color: 'text-green-600' }, + 'issues_archive': { title: '🗃️ 폐기함', icon: 'fas fa-archive', color: 'text-gray-600' } + }, + '시스템 관리': { + 'projects_manage': { title: '프로젝트 관리', icon: 'fas fa-folder-open', color: 'text-indigo-600' }, + 'daily_work': { title: '일일 공수', icon: 'fas fa-calendar-check', color: 'text-blue-600' }, + 'reports': { title: '보고서', icon: 'fas fa-chart-bar', color: 'text-red-600' }, + 'users_manage': { title: '사용자 관리', icon: 'fas fa-users-cog', color: 'text-purple-600' } + } }; - gridContainer.innerHTML = Object.entries(pages).map(([pageName, title]) => ` -
- - -
- `).join(''); + let html = ''; + // 카테고리별로 그룹화하여 표시 + Object.entries(pageCategories).forEach(([categoryName, pages]) => { + html += ` +
+

+ ${categoryName} +

+
+ `; + + Object.entries(pages).forEach(([pageName, pageInfo]) => { + const isChecked = currentPermissions[pageName] || false; + const isDefault = currentPermissions[pageName] === undefined ? + (pageInfo.title.includes('등록') || pageInfo.title.includes('조회') || pageInfo.title.includes('수신함')) : false; + + html += ` +
+ + +
+ `; + }); + }); + + gridContainer.innerHTML = html; grid.classList.remove('hidden'); } @@ -615,13 +621,19 @@ statusSpan.textContent = ''; try { - // 체크박스 상태 수집 - const pages = ['issues_create', 'issues_view', 'issues_manage', 'projects_manage', 'daily_work', 'reports']; + // 체크박스 상태 수집 (모든 페이지 포함) + const allPages = [ + 'issues_create', 'issues_view', 'issues_manage', + 'issues_inbox', 'issues_management', 'issues_archive', + 'projects_manage', 'daily_work', 'reports', 'users_manage' + ]; const permissions = {}; - pages.forEach(pageName => { + allPages.forEach(pageName => { const checkbox = document.getElementById(`perm_${pageName}`); - permissions[pageName] = checkbox.checked; + if (checkbox) { + permissions[pageName] = checkbox.checked; + } }); // 실제 API 호출로 권한 저장