refactor(admin): 학습센터 관리에서 활성/비활성 제거, 네비에 관리자·관리자 off
- learning-admin: 관리자 모드 토글·인라인 토큰 폼 삭제, 안내 문구는 좌측 메뉴 관리자로 통일 - nav: 관리자 세션 시 로그오프 대신 관리자(모달)·관리자 off(/admin/logout→/learning) - styles: 미사용 관리자 토글 스타일 정리 - README: 관리자 off 동작 반영 Made-with: Cursor
This commit is contained in:
@@ -65,7 +65,7 @@
|
||||
- 초기 샘플 데이터 시드
|
||||
- `resources/lecture`에 있는 `.pptx`를 최초 실행 시 자동 등록
|
||||
- **관리자 인증·바로가기(UI)**
|
||||
- **좌측 메뉴 하단 `관리자`**: 운영(OPS)에서 **이메일 인증**으로 로그인한 임직원에게도 표시됩니다. 클릭하면 모달에서 `ADMIN_TOKEN`을 입력해 검증한 뒤 `/admin`으로 이동합니다(`POST /api/admin/validate-token`). 이메일 미로그인 환경에서도 동일한 하단 항목으로 관리자 인증을 할 수 있습니다. 관리자 세션이 잡히면 같은 영역에 **사용자 현황관리**·**로그오프**(관리자 세션 종료) 등이 이어서 보입니다.
|
||||
- **좌측 메뉴 하단 `관리자` / `관리자 off`**: 운영(OPS)에서 **이메일 인증**으로 로그인한 임직원에게도 표시됩니다. **`관리자`**는 모달에서 `ADMIN_TOKEN`을 입력해 검증한 뒤 `/admin`으로 이동합니다(`POST /api/admin/validate-token`). **`관리자 off`**는 관리자 쿠키를 지우고 학습센터 목록(`/learning`)으로 돌아갑니다(`GET /admin/logout`). 이메일 미로그인 환경에서도 동일합니다. 관리자 세션이 잡히면 같은 영역에 **사용자 현황관리** 등이 함께 보입니다.
|
||||
- **학습센터** (`/learning`): 관리자 쿠키가 있을 때 상단 오른쪽 **학습 등록**으로 통합 관리 화면(`/admin`)에 들어갈 수 있습니다. 이메일(OPS) 로그인과 동시에 있어도 버튼이 숨겨지지 않습니다.
|
||||
- **AI 성공 사례** (`/ai-cases`): 관리자일 때 상단 **사례 등록·관리**로 편집 화면(`/ai-cases/write`)에 진입합니다(동일하게 OPS 로그인 중에도 표시).
|
||||
|
||||
|
||||
@@ -919,11 +919,6 @@ button.ai-case-inline-link:hover {
|
||||
}
|
||||
|
||||
.admin-mode-header {
|
||||
display: flex;
|
||||
flex-wrap: wrap;
|
||||
align-items: center;
|
||||
justify-content: space-between;
|
||||
gap: 12px;
|
||||
margin-bottom: 12px;
|
||||
}
|
||||
|
||||
@@ -931,75 +926,6 @@ button.ai-case-inline-link:hover {
|
||||
margin: 0;
|
||||
}
|
||||
|
||||
.admin-mode-toggle {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
gap: 12px;
|
||||
flex-wrap: wrap;
|
||||
}
|
||||
|
||||
.admin-status {
|
||||
font-size: 13px;
|
||||
font-weight: 600;
|
||||
padding: 4px 10px;
|
||||
border-radius: 999px;
|
||||
}
|
||||
|
||||
.admin-status.active {
|
||||
background: #dcfce7;
|
||||
color: #166534;
|
||||
}
|
||||
|
||||
.admin-status.inactive {
|
||||
background: #fef3c7;
|
||||
color: #92400e;
|
||||
}
|
||||
|
||||
.btn-admin-off {
|
||||
display: inline-block;
|
||||
padding: 6px 14px;
|
||||
font-size: 13px;
|
||||
color: #6b7280;
|
||||
background: #f3f4f6;
|
||||
border: 1px solid #e5e7eb;
|
||||
border-radius: 8px;
|
||||
text-decoration: none;
|
||||
}
|
||||
|
||||
.btn-admin-off:hover {
|
||||
background: #e5e7eb;
|
||||
color: #374151;
|
||||
}
|
||||
|
||||
.admin-activate-inline {
|
||||
display: inline-flex;
|
||||
align-items: center;
|
||||
gap: 8px;
|
||||
flex-wrap: wrap;
|
||||
}
|
||||
|
||||
.admin-activate-inline input[type="password"] {
|
||||
padding: 6px 10px;
|
||||
border: 1px solid #d1d5db;
|
||||
border-radius: 8px;
|
||||
font-size: 14px;
|
||||
min-width: 140px;
|
||||
}
|
||||
|
||||
.admin-activate-inline button {
|
||||
padding: 6px 14px;
|
||||
font-size: 13px;
|
||||
background: #f59e0b;
|
||||
color: #fff;
|
||||
border: none;
|
||||
border-radius: 8px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.admin-activate-inline button:hover {
|
||||
background: #d97706;
|
||||
}
|
||||
|
||||
.admin-inline {
|
||||
display: flex;
|
||||
gap: 8px;
|
||||
|
||||
@@ -37,23 +37,6 @@
|
||||
<section class="panel admin-panel">
|
||||
<div class="admin-mode-header">
|
||||
<h2>관리자 모드</h2>
|
||||
<div class="admin-mode-toggle">
|
||||
<% if (adminMode) { %>
|
||||
<span class="admin-status active">활성</span>
|
||||
<a href="<%= adminBasePath %>?q=<%= filters.q %>&type=<%= filters.type %>&tag=<%= filters.tag %>&category=<%= filters.category || '' %>&page=<%= pagination.page %>" class="btn-admin-off">비활성화</a>
|
||||
<% } else { %>
|
||||
<span class="admin-status inactive">비활성</span>
|
||||
<form action="<%= adminBasePath %>" method="get" class="admin-activate-inline">
|
||||
<input type="hidden" name="q" value="<%= filters.q %>" />
|
||||
<input type="hidden" name="type" value="<%= filters.type %>" />
|
||||
<input type="hidden" name="tag" value="<%= filters.tag %>" />
|
||||
<input type="hidden" name="category" value="<%= filters.category || '' %>" />
|
||||
<input type="hidden" name="page" value="<%= pagination.page %>" />
|
||||
<input type="password" name="token" placeholder="관리자 토큰" required autocomplete="off" />
|
||||
<button type="submit">활성화</button>
|
||||
</form>
|
||||
<% } %>
|
||||
</div>
|
||||
</div>
|
||||
<% if (retryQueued > 0) { %>
|
||||
<p class="admin-ok">실패 건 재시도 <%= retryQueued %>건이 큐에 등록되었습니다.</p>
|
||||
@@ -74,7 +57,7 @@
|
||||
<% if (adminRequested) { %>
|
||||
<p class="admin-error">입력한 토큰이 올바르지 않습니다. 다시 확인해주세요.</p>
|
||||
<% } %>
|
||||
<p class="admin-warn">삭제·썸네일 관리는 관리자 토큰을 입력한 뒤 <strong>활성화</strong>를 눌러주세요.</p>
|
||||
<p class="admin-warn">삭제·썸네일 관리는 좌측 메뉴 하단 <strong>관리자</strong>에서 토큰을 입력해 주세요.</p>
|
||||
<% } %>
|
||||
</section>
|
||||
<div
|
||||
@@ -173,7 +156,7 @@
|
||||
<span class="count-chip">총 <%= pagination.totalCount %>건</span>
|
||||
</div>
|
||||
<% if (!adminMode && lectures.length > 0) { %>
|
||||
<p class="admin-warn" style="margin-bottom:12px">수정·삭제를 하려면 위에서 관리자 토큰을 입력하고 <strong>관리자 활성화</strong>를 눌러주세요.</p>
|
||||
<p class="admin-warn" style="margin-bottom:12px">수정·삭제는 좌측 메뉴 하단 <strong>관리자</strong>에서 토큰을 입력한 뒤 이용할 수 있습니다.</p>
|
||||
<% } %>
|
||||
<form action="<%= adminBasePath %>" method="get" class="filter-grid" style="margin-bottom:12px">
|
||||
<input type="hidden" name="token" value="<%= tokenRaw %>" />
|
||||
|
||||
@@ -35,7 +35,8 @@
|
||||
<% if (_admin) { %>
|
||||
<a href="/admin/users" class="nav-item <%= activeMenu === 'admin-users' ? 'active' : '' %>">사용자 현황관리</a>
|
||||
<div class="nav-separator"></div>
|
||||
<a href="/admin/logout" class="nav-item nav-item-ghost" title="관리자 세션 종료">로그오프</a>
|
||||
<button type="button" class="nav-item nav-item-admin-entry" onclick="openAdminTokenModal()" title="관리자 토큰 입력">관리자</button>
|
||||
<a href="/admin/logout" class="nav-item nav-item-ghost" title="관리자 모드 종료 후 학습센터 목록으로">관리자 off</a>
|
||||
<a href="/logout" class="nav-item nav-item-ops-logout" title="이메일 인증 세션 종료">로그아웃</a>
|
||||
<% } else { %>
|
||||
<div class="nav-separator nav-separator-footer-admin"></div>
|
||||
@@ -45,7 +46,8 @@
|
||||
<% } else if (_admin) { %>
|
||||
<a href="/admin/users" class="nav-item <%= activeMenu === 'admin-users' ? 'active' : '' %>">사용자 현황관리</a>
|
||||
<div class="nav-separator"></div>
|
||||
<a href="/admin/logout" class="nav-item nav-item-ghost" title="관리자 세션 종료">로그오프</a>
|
||||
<button type="button" class="nav-item nav-item-admin-entry" onclick="openAdminTokenModal()" title="관리자 토큰 입력">관리자</button>
|
||||
<a href="/admin/logout" class="nav-item nav-item-ghost" title="관리자 모드 종료 후 학습센터 목록으로">관리자 off</a>
|
||||
<% } else { %>
|
||||
<div class="nav-separator"></div>
|
||||
<button type="button" class="nav-item nav-item-ghost" onclick="openAdminTokenModal()" title="관리자 모드">관리자</button>
|
||||
|
||||
Reference in New Issue
Block a user