/* ============================================================================= * M02_MasterTemplete_Spreadsheet_Trial.ts * ⚠ 임시 — [스프레드시트 시험] 단추(사용자 지시 · 스프레드시트 1단계 검증 뒤 지움: * 이 파일 · `M02_MasterTemplete_UI_Main.ts` 의 시험 단추 · Api_Fetch `*SpreadsheetTrial` · * Router `/spreadsheet-trial` · 저장 자리 `tmp/spreadsheet_trial.json`). * 빈 통합문서(시트 셋)를 메인 칸에 넓게 엶 · [시험 저장] = 서버가 같은 엔진으로 다시 풀어 tmp 에 적음. * 글자는 이 파일에 둠. * ========================================================================== */ import { createButton, el, showToast } from "@ui/ui_template_elements"; import type { SpreadsheetHandle, Workbook } from "../A00_Common/spreadsheet/spreadsheet"; import { readSpreadsheetTrial, saveSpreadsheetTrial } from "./M02_MasterTemplete_Api_Fetch"; import "./M02_MasterTemplete_Spreadsheet_Trial.css"; const TEXT = { save: "시험 저장", note: "임시 시험 화면 — 저장은 서버 tmp 견본 자리(작업 양식과 무관)", saved: "시험 통합문서를 저장했음(서버 재계산)", failed: "스프레드시트 시험 실패 — {value}", }; const why = (error: unknown): string => (error instanceof Error ? error.message : String(error)); export interface TrialHandle { getDoc: () => unknown; destroy: () => void; } /** `onDirty` = 고침 있음 · 저장 뒤 없음(페이지의 떠날 때 물음과 이음) */ export function mountSpreadsheetTrial( host: HTMLElement, onDirty: (dirty: boolean) => void, ): TrialHandle { let sheet: SpreadsheetHandle | null = null; let alive = true; const save = createButton({ label: TEXT.save, variant: "filled" }); const area = el("div", { className: "m02-trial__sheet" }); const root = el("div", { className: "m02-trial", children: [ el("div", { className: "m02-trial__bar", children: [el("span", { className: "m02-trial__note", text: TEXT.note }), save], }), area, ], }); host.replaceChildren(root); const fail = (error: unknown): void => showToast(TEXT.failed.replace("{value}", why(error)), "error"); void (async () => { try { const [{ createSpreadsheet }, got] = await Promise.all([ import("../A00_Common/spreadsheet/spreadsheet"), readSpreadsheetTrial(), ]); if (!alive) return; sheet = createSpreadsheet(area, got.문서 as Workbook, { onChange: () => onDirty(true), inspect: true, // ⚠ 임시 — 브레인 검증용 문맥(window.__aisloSheet) · 산출근거 카드는 안 넘김 }); } catch (error) { if (!alive) return; area.replaceChildren(el("p", { className: "m02-trial__empty", text: why(error) })); fail(error); } })(); save.addEventListener("click", async () => { if (!sheet) return; save.disabled = true; try { await saveSpreadsheetTrial(sheet.getDoc()); onDirty(false); showToast(TEXT.saved, "success"); } catch (error) { fail(error); } finally { save.disabled = false; } }); return { getDoc: () => sheet?.getDoc() ?? null, destroy: () => { alive = false; sheet?.destroy(); root.remove(); }, }; }