merge(M02): origin/sub_laptop_3 받음 — Structure.ts import 충돌 풂(getActiveOwner 더함 · readTemplate 뺌)

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01BVPp2o6Mh2FZJr72yW3ofZ
This commit is contained in:
2026-10-04 18:30:44 +09:00
co-authored by Claude Opus 5.5
3 changed files with 43 additions and 18 deletions
@@ -24,15 +24,15 @@ import {
import { openModal } from "@ui/ui_template_modal";
import type { LinkOptions } from "../A00_Common/spreadsheet/spreadsheet_links";
import { searchMaterials } from "../M01_MasterData/M01_MasterData_Api_Fetch";
import { fetchComboInputs, fetchUsableCombos } from "./M02_MasterTemplete_Labor_Api";
import { fetchUsableCombos } from "./M02_MasterTemplete_Labor_Api";
import {
copyArea,
copyMaterial,
copyStructure,
fetchLaborPills,
fetchStructureNumbers,
getActiveLayer,
getActiveOwner,
readTemplate,
saveTemplate,
type StructureNumbers,
type TreeEdit,
@@ -70,9 +70,8 @@ const TEXT = {
copied: "복사해 가져옴",
acrossLater: "다른 곳(층 · 사람)에서 가져오기는 서버 길이 선 뒤 — 지금은 같은 곳만",
copyFailed: "복사 실패 — {value}",
noPrice: "이 열에 일위대가가 없어 알약 없음 — 구조물 조합 일위대가 줄에서 고름",
noInputs: "일위대가 {value} 에 입력값이 없어 알약 없음",
inputsFailed: "일위대가 입력값을 못 받음 — {value}",
noPills: "이 열 일위대가에 담은 로직 · 자재가 없어 알약 없음 — 일위대가 상세에서 담음",
pillsFailed: "일위대가 알약을 못 받음 — {value}",
discardCards: "카드(도면 · 면적산출 · 재료산출)에 저장 안 한 고침이 있음 — 버리고 넘어갈까?",
};
@@ -278,7 +277,8 @@ export const columnHead = (col: StructureColumn): string =>
export const structureLabel = (number: string, col: StructureColumn): string =>
[number, columnHead(col)].filter(Boolean).join(" ");
/** 면적산출 · 재료산출 편집 화면 위 알약 막대 — 면적 = 그 열 일위대가 입력값(물량) · 재료 = 자재DB 찾기.
/** 면적산출 · 재료산출 편집 화면 아래 알약 막대 — 면적 = 그 열 일위대가의 로직 물량 「이름|단위」 + 자재 「자재|MT키」
* (서버 pills 길 · 39-4 · 다 `고정` — 더하기 · 빼기는 일위대가 쪽) · 재료 = 자재DB 찾기.
* 알약이 없으면 까닭 글(`notice`)을 같이 돌려줌 */
export async function pillsFor(
kind: SheetKind,
@@ -288,20 +288,19 @@ export async function pillsFor(
const own = await inputPills(column, "재료");
return { links: { 항목: own, 모드: "자재", 자재찾기: searchMaterials } };
}
const own = await inputPills(column, "면적"); // 선택 입력 카드가 면적산출로 고른 입력
const none = (notice: string) => ({ links: { 항목: own, 모드: "입력" as const }, notice });
const table = await readTemplate(getActiveLayer(), "table", STRUCTURE_TABLE, null).catch(
() => null,
);
const cols = (table?.문서 as { 열?: { id: string; 일위대가?: string | null }[] } | null)?.열;
const combo = cols?.find((c) => c.id === column)?.일위대가;
if (!combo) return none(TEXT.noPrice);
const none = (notice: string) => ({ links: { 항목: [], 모드: "입력" as const }, notice });
try {
const got = await fetchComboInputs(combo);
const 항목 = [...got.물량.map((q) => ({ 키: q.키, 이름: q.이름, 단위: q.단위 })), ...own];
return 항목.length ? { links: { 항목, 모드: "입력" } } : none(fill(TEXT.noInputs, combo));
const { 알약 } = await fetchLaborPills(column);
const 항목 = 알약.map((p) => ({
키: p.키,
이름: p.이름,
단위: p.단위,
...(p.자재 ? { 자재: p.자재 } : {}),
고정: true,
}));
return 항목.length ? { links: { 항목, 모드: "입력" } } : none(TEXT.noPills);
} catch (error) {
return none(fill(TEXT.inputsFailed, why(error)));
return none(fill(TEXT.pillsFailed, why(error)));
}
}