동의 게이트와 런타임 안정화

This commit is contained in:
Yun Chan 2026-06-27 17:22:38 +09:00
parent 0eb7d925ed
commit 0ec266a761
34 changed files with 1186 additions and 158 deletions

View file

@ -8,7 +8,6 @@ import {
Input,
Kicker,
Panel,
SectionHead,
type IconName,
} from "../components/ui";
import { roleLabel, useAuth } from "../lib/auth";
@ -158,6 +157,13 @@ export default function Settings() {
const affiliationDirtyRef = useRef(false);
const engineConfigRef = useRef<AdminEngineConfigResponse | null>(null);
useEffect(() => {
document.body.setAttribute("data-page", "settings");
return () => {
document.body.removeAttribute("data-page");
};
}, []);
const flashSaved = (key: string) => {
setSavedKey(key);
if (savedTimer.current) window.clearTimeout(savedTimer.current);
@ -365,23 +371,7 @@ export default function Settings() {
const engineServiceStatus = engineService?.status ?? "degraded";
return (
<AppShell contextLabel="설정">
<div className="vg-set__mast">
<SectionHead
kicker="설정"
title="계정과 학습 환경을 관리합니다"
desc="계정 표시 정보, 음성, 알림, 운영 설정을 한 곳에서 관리합니다."
/>
<div className="vg-set__mast-meta" aria-label="설정 상태">
<span className="vg-set__pill">{roleLabel(role)}</span>
{isAdmin ? (
<span className={`vg-set__pill vg-set__pill--${engineServiceStatus}`}>
AI {healthStatusLabel(engineService?.status)}
</span>
) : null}
</div>
</div>
<AppShell contextLabel="설정" hideNav hideTopbar bleed>
{error ? (
<div className="vg-set__callout vg-set__callout--warn" role="alert">
<span className="vg-set__callout-ico">
@ -393,6 +383,16 @@ export default function Settings() {
<div className="vg-set" aria-busy={loading}>
<aside className="vg-set__rail">
<div className="vg-set__rail-title">
<span className="vg-set__rail-mark" aria-hidden="true">
<Icon name="settings" size={24} strokeWidth={2} />
</span>
<div>
<h1></h1>
<p> </p>
</div>
</div>
<div className="vg-set__rail-card" aria-label="계정 요약">
<div className="vg-set__rail-avatar" aria-hidden="true">
{initials}
@ -424,6 +424,15 @@ export default function Settings() {
</button>
))}
</nav>
<div className="vg-set__rail-status" aria-label="설정 상태">
<span className="vg-set__pill">{roleLabel(role)}</span>
{isAdmin ? (
<span className={`vg-set__pill vg-set__pill--${engineServiceStatus}`}>
AI {healthStatusLabel(engineService?.status)}
</span>
) : null}
</div>
</aside>
<div className="vg-set__forms">