feat(M02): 일위대가 사전조합 — 층 단추 따로 · 명시 owner · 구분 › 상세구분 2단 나무(134-3)

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01SE9MxeXTu2uaDZ55BJowAY
This commit is contained in:
2026-10-09 15:01:16 +09:00
co-authored by Claude Opus 5.5
parent 15f2e7c4f5
commit 66efaf2834
16 changed files with 466 additions and 94 deletions
+12 -3
View File
@@ -1,8 +1,8 @@
/* =============================================================================
* M02_MasterTemplete_Layer.ts
* M02 한 화면의 뿌리 셋(마스터 · 회사 · 개인 · PLAN 27-1) — 진입 해시
* `#/m02-master-template?open=구조물조합|옵션|도면&root=master|company|personal&owner=…&company=…`
* (옛 `?layer=` 도 root 로 읽음) · 고칠 권한(`accessFor` — 서버 `M02_Layer_Access` 와 짝 · 27-1c) ·
* `#/m02-master-template?open=구조물조합|옵션|도면&root=master|company|personal&owner=…&company=…&pre=…`
* (옛 `?layer=` 도 root 로 읽음 · `pre` = 일위대가 사전조합 층 · 134-3) · 고칠 권한(`accessFor` — 서버 `M02_Layer_Access` 와 짝 · 27-1c) ·
* 회사 없음 안내 · 회사용 읽기만일 때 [개인용으로 복사] 막대.
* ========================================================================== */
@@ -25,9 +25,12 @@ export interface Entry {
open: OpenTarget;
/** 시스템 관리자가 보는 회사(PLAN 29 · 없으면 sessionStorage `aislo.adminCompany` · 자기 회사) */
company: string | null;
/** 일위대가 사전조합 층(134-3 · 페이지 층과 따로) — 없으면 기본(`defaultRoot`) */
pre: Root | null;
}
const OPENS: OpenTarget[] = ["구조물조합", "옵션", "도면", "일위대가조합"];
const ROOTS: Root[] = ["master", "company", "personal"];
export const layerOfRoot = (root: Root): ManageLayer => (root === "master" ? "system" : root);
@@ -38,7 +41,8 @@ export function entryFromHash(): Entry {
const root: Root = raw === "company" || raw === "personal" ? raw : "master";
const open = OPENS.find((one) => one === query.get("open")) ?? "구조물조합";
const owner = root === "master" ? null : query.get("owner") || null;
return { root, owner, open, company: query.get("company") || null };
const pre = ROOTS.find((one) => one === query.get("pre")) ?? null;
return { root, owner, open, company: query.get("company") || null, pre };
}
/** 진입 해시 인자 — `navigateTo(ROUTES.M02_MASTER_TEMPLATE, entryQuery(…))` */
@@ -47,8 +51,13 @@ export const entryQuery = (entry: Entry): Record<string, string> => ({
root: entry.root,
...(entry.owner ? { owner: entry.owner } : {}),
...(entry.company ? { company: entry.company } : {}),
...(entry.pre ? { pre: entry.pre } : {}),
});
/** 기본 층(134-4) — 내 개인 층이 있으면 개인 · 회사 없으면 마스터 */
export const defaultRoot = (user: SessionUser | null): Root =>
ownOwner("personal", user) ? "personal" : "master";
/** 볼 회사 — 시스템 관리자 = 해시 `company` · sessionStorage `aislo.adminCompany`(대시보드가 넣음) ·
* 자기 회사 차례 · 그 밖 = 자기 회사 · 없으면 null */
export function viewCompany(entry: Entry, user: SessionUser | null): string | null {