Files
sam-docs/plans/item-master-data-alignment-plan.md
권혁성 6b8b70a74f docs: BOM 품목 매핑, 수주 개소관리, 배포 가이드 문서 추가
- BOM 품목 매핑 분석 및 계획 문서
- 수주 개소(노드) 관리 계획 문서
- 배포 가이드 문서
- 수입검사 양식 변경 이력 업데이트

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-24 10:02:47 +09:00

46 KiB
Raw Blame History

품목 기준 데이터 정비 계획

작성일: 2026-01-31 목적: 5130 레거시 시스템에서 이관된 품목 데이터가 SAM 품목기준관리(item-master-data-management)에서 올바르게 표시되고, 견적 문서에 정확히 반영되도록 설정을 정비한다. 기준 문서: docs/specs/database-schema.md, docs/rules/item-policy.md 상태: 🔄 진행중


📍 현재 진행 상태

항목 내용
마지막 완료 작업 견적 영향 검증 완료 + SM/CS 프론트엔드 검증 + SM display_condition 수정
다음 작업 섀도잉 정리 (재수행), SM field 108/109 드롭다운 옵션 실데이터 정비
진행률 Phase 1 완료, Phase 2A 롤백, Phase 2B 완료 (5/5 + 검증 + RM/SM display_condition 수정 + 견적 검증)
마지막 업데이트 2026-02-03

1. 개요

1.1 배경

5130 레거시 시스템(chandj DB)의 품목 데이터를 SAM으로 이관 완료하였으나, SAM의 품목기준관리(item-master-data-management) 설정이 이관된 데이터 구조와 맞지 않아 프론트엔드에서 품목 정보가 올바르게 표시되지 않는다. 품목 데이터가 정확히 표시되어야 견적 문서에 데이터를 뿌려줄 수 있다.

핵심 문제:

  • item_pages/item_sections/item_fields의 현재 필드 정의가 이관된 데이터의 실제 attributes JSON 구조와 불일치
  • item_details 테이블에 FG 18개 품목의 상세 정보가 없음 (PT 129개만 존재)
  • 드롭다운 필드의 options 값이 실제 데이터와 매핑되지 않음
  • setting_field_defstenant_field_settings 테이블이 비어있음

1.2 기준 원칙

┌─────────────────────────────────────────────────────────────────┐
│  🎯 핵심 원칙                                                     │
├─────────────────────────────────────────────────────────────────┤
│  1. 견적 로직(FormulaEvaluatorService)에 영향 없는 범위에서만 수정  │
│  2. items.bom JSON 구조, items.code 체계는 변경 금지                │
│  3. item_pages/sections/fields 설정만 조정하여 데이터 표시 정합성 확보│
│  4. 5130 데이터와 SAM 데이터 간 매핑 관계를 명확히 문서화           │
└─────────────────────────────────────────────────────────────────┘

1.3 변경 승인 정책

분류 예시 승인
즉시 가능 item_fields options 값 수정, field_name 변경, 필드 순서 변경 불필요
⚠️ 컨펌 필요 item_fields 추가/삭제, item_sections 구조 변경, entity_relationships 변경 필수
🔴 금지 items.bom JSON 구조 변경, items.code 체계 변경, FormulaEvaluatorService 수정 별도 협의

1.4 준수 규칙

  • docs/specs/database-schema.md - DB 스키마 참조
  • docs/rules/item-policy.md - 품목 정책
  • docs/standards/quality-checklist.md - 품질 체크리스트

2. 대상 범위

2.1 Phase 1: 분석 (4단계)

# 작업 항목 상태 비고
1.1 품목기준관리 구조 파악 아래 섹션 4.1 참조
1.2 현재 설정 현황 분석 아래 섹션 4.2 참조
1.3 이관된 제품 데이터 구조 분석 아래 섹션 4.3 참조
1.4 BOM 관계 구조 분석 아래 섹션 4.4 참조

2.2 Phase 2A: 설정 수정 (롤백됨)

⚠️ 2026-01-31 DB 복원으로 전체 롤백됨 Phase 2A에서 PT Part_type options 값을 변경했으나, display_conditionexpectedValue와 불일치하여 조건부 화면 표시가 깨짐 (원본: "조립 부품(Assembly Part)" → 변경: "조립부품"). DB 백업에서 복원하여 전체 롤백.

# 작업 항목 상태 비고
2.1 FG(제품) 필드 설정 정비 🔄 롤백 DB 복원으로 롤백. 아래 2B-1에서 재수행
2.2 PT(부품) 필드 설정 정비 🔄 롤백 display_condition 깨짐으로 롤백
2.3 SM/RM/CS 필드 설정 정비 🔄 롤백 DB 복원으로 롤백. 아래 2B-1에서 재수행
2.4 FG item_details 데이터 보완 🔄 롤백 DB 복원으로 롤백
2.5 드롭다운 options 실데이터 매핑 🔄 롤백 DB 복원으로 롤백
2.6 고정컬럼-동적필드 섀도잉 정리 🔄 롤백 DB 복원으로 롤백

롤백 교훈:

  • options value 변경 시 반드시 display_condition.expectedValue 동기화 확인
  • 기존 값은 교체(REPLACE)가 아닌 추가(ADD)로 접근
  • 설정 구조 변경보다 데이터 정비를 먼저 수행

2.3 Phase 2B: 데이터 우선 정비 (현재 진행)

접근 방식 변경: "품목기준관리는 그대로 두고 데이터만 먼저 맞추자"

  • 기존 설정 삭제/교체 금지, 추가만 허용
  • 데이터 분류 및 매핑을 먼저 완료한 후 설정 조정
# 작업 항목 상태 비고
2B-1 필드 추가 (FG 4개 + SM/RM options ADD) FG id:177-180 추가, SM id:107 기존+11종 추가, RM id:100-104 기존+실데이터 추가
2B-2 BOM 확인 FG 18건 BOM 이미 정상 구성됨
2B-3 category_id 분류 categories 5건 추가(id:298-302), 780건 전체 매핑 완료
2B-4 FG item_details 생성 18건 INSERT 완료 (id:524-541), product_category/item_name/specification 설정
2B-5 PT/SM/RM/CS attributes 매핑 정비 PT: Part_type 669건 매핑 (조립400/구매205/절곡64). RM: 100~103 field_key 28건. SM: 107 카테고리 61건. CS: item_name 4건

3. 작업 절차

3.1 단계별 절차

Step 1: 구조 분석 (Phase 1.1)
├── item_pages → item_sections → item_fields 계층 구조 파악
├── entity_relationships 연결 관계 매핑
└── React 프론트엔드 렌더링 로직 확인

Step 2: 현재 설정 현황 (Phase 1.2)
├── 5개 item_pages (CS/RM/SM/PT/FG) 설정 현황
├── 26개 page→section, 66개 section→field 관계 확인
└── 각 필드의 options, validation_rules 점검

Step 3: 이관 데이터 구조 (Phase 1.3)
├── items 테이블 780건 (FG:18, PT:669, SM:61, RM:28, CS:4)
├── items.attributes JSON 구조 분석
├── item_details 129건 (PT만 존재) 분석
└── 5130 원본 데이터와 대조

Step 4: BOM 관계 구조 (Phase 1.4)
├── FG→PT BOM JSON 관계 매핑
├── 5130 models→parts→parts_sub 3계층 대응
├── BD계열(가이드레일, 하단마감재, L-BAR) 매핑
└── 견적 FormulaEvaluatorService 의존성 확인

Step 5: 설정 수정 (Phase 2)
├── FG 필드: attributes 키와 item_fields 매핑
├── PT 필드: part_type별 분기 필드 정의
├── 드롭다운 options: 실제 사용 값으로 갱신
├── FG item_details 18건 생성
├── 고정컬럼-동적필드 섀도잉 정리 (is_active 중복 통합, null key, 미연결 필드)
└── 프론트엔드 표시 검증

4. 상세 분석 결과

4.1 Phase 1.1: 품목기준관리 구조

아키텍처 개요

┌─────────────────────────────────────────────────────────────────┐
│  item_pages (품목유형별 폼 정의)                                   │
│  - CS/RM/SM/PT/FG 각 1개 페이지                                   │
│  - tenant_id=287, group_id=1                                     │
├─────────────────────────────────────────────────────────────────┤
│  entity_relationships (parent_type='page' → child_type='section')│
│  - 26개 관계 (페이지→섹션)                                        │
│  - 66개 관계 (섹션→필드)                                          │
├─────────────────────────────────────────────────────────────────┤
│  item_sections (섹션)                                             │
│  - type: 'fields' (일반 필드 그룹)                                │
│  - type: 'bom' (BOM 구성 섹션)                                    │
├─────────────────────────────────────────────────────────────────┤
│  item_fields (필드 정의)                                          │
│  - field_type: textbox/number/dropdown/checkbox/date/textarea    │
│  - storage_type: 'column' (items 컬럼) / 'json' (attributes)    │
│  - options: JSON [{label, value}] (드롭다운용)                    │
└─────────────────────────────────────────────────────────────────┘

테이블 스키마

item_pages: id, tenant_id, group_id, page_name, item_type(ENUM), source_table, absolute_path, is_active

item_sections: id, tenant_id, group_id, title, type(ENUM: fields/bom), order_no, is_template, is_default, description

item_fields: id, tenant_id, group_id, field_name, field_key, field_type(ENUM), order_no, is_required, default_value, placeholder, display_condition(JSON), validation_rules(JSON), options(JSON), properties(JSON), source_table, source_column, storage_type(ENUM: column/json), json_path, category, description, is_common, is_active, is_locked

entity_relationships: id, tenant_id, group_id, parent_type, parent_id, child_type, child_id, order_no, metadata(JSON), is_locked


4.2 Phase 1.2: 현재 설정 현황

4.2.1 페이지별 구조

CS (소모품) - page id:1015

└ Section: 기본정보 (id:92, type:fields)
    ├ 품목명 (key:item_name, textbox)
    ├ 규격(사양) (key:specification, textbox)
    ├ 단위 (key:unit, dropdown)
    └ 비고 (key:note1, textbox)

RM (원자재) - page id:1016

└ Section: 기본 정보 (id:93, type:fields)
    ├ 품목명 (key:100_item_name, dropdown) → options: [철판, 알루미늄, 스테인리스, 아연도금강판]
    ├ 규격 (key:101_specification_1, dropdown) → options: [옵션1-1, 옵션1-2, 옵션1-3, 옵션120]
    ├ 규격 (key:102_specification_2, dropdown) → options: [옵션2-1, 옵션2-2]
    ├ 규격 (key:103_specification_3, dropdown) → options: [옵션3-1, 옵션3-2, 옵션3-3]
    ├ 규격 (key:104_specification_4, dropdown)
    ├ 활성 여부 (key:is_active, dropdown)
    ├ 단위 (key:unit, dropdown)
    └ 비고 (key:note1, textbox)

SM (부자재) - page id:1017

└ Section: 기본 정보 (id:94, type:fields)
    ├ 품목명 (key:107_item_name, dropdown)
    ├ 규격 (key:108_specification_1, dropdown)
    ├ 규격 (key:109_specification_2, dropdown)
    ├ 활성 여부 (key:field_163, dropdown)
    ├ 단위 (key:unit, dropdown)
    └ 비고 (key:note1, textbox)

PT (부품) - page id:1018

├ Section: 기본 정보 (id:95, type:fields)
│   ├ 부품 유형 (key:Part_type, dropdown)
│   ├ 품목명 (key:itemNameAssemblyPart, dropdown)
│   ├ 설치유형 (key:119~121_Installation_type_1~3, dropdown x3)
│   ├ 마감 (key:112_deadline, dropdown)
│   ├ 품목명 (key:122_bending_parts, dropdown)
│   ├ 종류 (key:123~125_type_1~3, dropdown x3)
│   ├ 재질 (key:126_texture, dropdown)
│   ├ 폭 합계 (key:127_width_total, number)
│   ├ 모양&길이 (key:128_Shape_Length, dropdown)
│   ├ 비고 (key:note2, textbox)
│   ├ 품목명 (key:132_PurchasedItemName, dropdown)
│   ├ 품목상태 (key:138_state, dropdown)
│   ├ 전원 (key:134_power, dropdown)
│   ├ 용량 (key:135_capacity, dropdown)
│   ├ 비고 (key:note3, textbox)
│   ├ 품목상태 (key:, dropdown) ← ⚠️ key 비어있음
│   └ 단위 (key:unit, dropdown)
├ Section: 측면 규격 및 길이 (id:99, type:fields)
│   ├ 측면 규격 (가로) (key:113_side_dimensions_horizontal, number)
│   ├ 측면 규격 (세로) (key:114_side_dimensions_vertical, number)
│   ├ 길이 (key:115_length, dropdown)
│   ├ 품목 상태 (key:105_state, dropdown)
│   └ 품목상태 (key:133_state, dropdown)
├ Section: BOM (id:100, type:fields)
│   └ 부품구성 (BOM) 필요 (key:118_bom, checkbox)
└ Section: 부품 구성 (BOM) (id:101, type:bom)

FG (제품) - page id:1019

├ Section: 기본 정보 (id:102, type:fields)
│   ├ 상품명 (key:139_productName, textbox)
│   ├ 품목명 (key:140_field_96, textbox)
│   ├ 로트 약자 (key:141_lotNum, textbox)
│   ├ 품목상태 (key:138_state, dropdown)
│   ├ 비고 (key:note3, textbox)
│   ├ 인정번호 (key:142_accreditationNumber, textbox)
│   ├ 인정 유효기간 시작일 (key:143_accreditationStart, date)
│   ├ 인정 유효기간 종료일 (key:144_accreditationEnd, date)
│   └ 비고 (key:145_field_137, textbox)
├ Section: BOM (id:100, type:fields) ← PT와 공유
│   └ 부품구성 (BOM) 필요 (key:118_bom, checkbox)
└ Section: 부품 구성 (BOM) (id:101, type:bom) ← PT와 공유

4.2.2 발견된 문제점

# 문제 영향 심각도
1 FG 필드의 field_key가 이관 데이터의 attributes 키와 불일치 FG 품목 표시 불가 🔴
2 PT 필드에 field_key가 빈 필드 존재 데이터 매핑 실패 🟡
3 RM/SM 드롭다운 options가 플레이스홀더 값 (옵션1-1 등) 실제 데이터와 불일치 🟡
4 FG item_details 0건 (18개 FG 품목 상세 없음) 제품 상세 표시 불가 🔴
5 setting_field_defs, tenant_field_settings 테이블 비어있음 필드 커스터마이징 미설정 🟢
6 FG attributes에 model_name, finishing_type 등 레거시 키 사용 필드 매핑 필요 🟡
7 고정컬럼과 동적필드 간 섀도잉 중복 다수 존재 향후 일괄 기능 오작동 위험 🔴

4.2.3 고정컬럼-동적필드 섀도잉 분석

is_common=1 필드 11개가 items 테이블 고정 컬럼과 직접 매핑됨. is_common=0 동적 필드 중 고정 컬럼과 의미적으로 동일한 필드가 별도 key로 생성되어 있어, 고정 컬럼 기반 기능(필터링, 일괄 변경 등)이 이 동적 필드를 사용하는 품목에 적용되지 않는 위험 존재.

고정 컬럼 매핑 현황 (is_common=1, 정상)
field id field_key source_column 비고
153 item_type items.item_type
154 code items.code
155 name items.name
156 items_unit items.unit
157 category_id items.category_id
158 bom items.bom
159 attributes items.attributes
160 attributes_archive items.attributes_archive
161 options items.options
162 description items.description
163 is_active items.is_active
섀도잉 유형 A: is_active 중복 (6건) — 🔴 이번에 정리
field id field_key field_name 소속 page 섀도잉 대상
163 is_active 활성 여부 공통(is_common=1) items.is_active (정상 매핑)
164 field_163 활성 여부 SM items.is_active 중복
105 105_state 품목 상태 PT (측면규격 섹션) items.is_active 중복
131 131_state 품목 상태 미연결 items.is_active 중복
133 133_state 품목상태 PT (측면규격 섹션) items.is_active 중복
138 138_state 품목상태 PT, FG items.is_active 중복
152 (null) 품목상태 PT items.is_active 중복 + key 없음

위험: items.is_active 기반 비활성 필터링 시 동적 필드 138_state 등을 사용하는 품목은 필터 미적용

섀도잉 유형 B: null key 필드 (1건) — 🔴 이번에 정리
field id field_key field_name 소속 page
152 (null) 품목상태 PT

위험: field_key가 없어서 데이터 저장/조회 자체 불가. 폼에 표시는 되지만 값 매핑 실패.

섀도잉 유형 C: 미연결 필드 (5건) — 🟡 이번에 정리

어떤 page에도 entity_relationship으로 연결되지 않아 사용 불가 상태인 필드:

field id field_key field_name 비고
116 116_bending_parts 품목명 미연결, 122와 중복
117 117_purchase_parts 품목명 미연결, 132와 중복
129 unit_2 단위_2 미연결, 98(unit)과 중복
131 131_state 품목 상태 미연결, is_active 중복
136 unit_3 단위_3 미연결, 98(unit)과 중복

위험: 미연결 상태이므로 즉각적 문제는 없으나, 향후 혼동 유발 가능.

섀도잉 유형 D: name/unit/specification/description 중복 — 📌 다음에 정리
고정 컬럼 동적 필드 중복 수 소속 pages 다음에 정리하는 이유
items.name 8건 (id:96,100,107,111,122,132,139,140) CS,RM,SM,PT,FG PT 부품유형별 분기 UI와 맞물림. 렌더링 로직 변경 필요
items.unit 2건 (id:98,129,136) CS,RM,SM,PT + 미연결 unit(id:98)은 4개 page에서 활발히 사용 중
item_details.specification 6건 (id:97,101104,108109) CS,RM,SM 원자재 4단 규격은 의도된 설계. 통합 시 정책 결정 필요
items.description 4건 (id:99,130,137,145) CS,RM,SM,PT,FG 용도별 비고 분리가 의도된 것일 수 있음
item_details.part_type 1건 (id:110) PT 현재 정상 사용 중
item_details.certification_* 3건 (id:142~144) FG FG item_details 생성 후 연계 검토

4.3 Phase 1.3: 이관된 제품 데이터 구조

4.3.1 SAM items 테이블 현황 (tenant_id=287)

item_type 건수 설명
FG (완제품) 18 5130 models 18개와 1:1 매핑
PT (부품) 669 5130 parts/parts_sub + BDmodels 이관
SM (부자재) 61 5130 item_list 중 부자재
RM (원자재) 28 5130 item_list 중 원자재
CS (소모품) 4 소모품
합계 780

4.3.2 FG 품목 attributes 구조

FG 18개 품목의 attributes JSON 구조 (예: FG-KSS01-벽면형-SUS):

{
    "model_name": "KSS01",        // 5130 모델명
    "legacy_source": "models",     // 원본 출처
    "finishing_type": "SUS마감",    // 마감 유형
    "guiderail_type": "벽면형",    // 가이드레일 유형 (설치유형)
    "major_category": "스크린",    // 대분류 (스크린/철재)
    "legacy_model_id": 12         // 5130 model_id
}

FG attributes 키 ↔ FG item_fields 매핑 현황:

attributes 키 현재 FG field_key 매핑 상태
model_name 139_productName (상품명) 불일치 - textbox로 직접 입력
major_category 없음 필드 없음
finishing_type 없음 필드 없음
guiderail_type 없음 필드 없음
legacy_model_id 없음 내부 참조용, 표시 불필요
legacy_source 없음 내부 참조용, 표시 불필요

4.3.3 PT 품목 attributes 구조

PT 품목의 attributes JSON (예: PT-가이드레일):

{
    "base_price": "25000.00",      // 기본 단가
    "legacy_num": 6,               // 5130 번호
    "legacy_source": "item_list"   // 원본 출처
}

4.3.4 item_details 현황

item_type item_details 건수 비고
FG 0 ⚠️ 없음 - 생성 필요
PT 129 BD계열 부품 (마구리, 케이스 등)
SM 0
RM 0
CS 0

PT item_details 예시 (BD-마구리-505*355):

part_type: 마구리
item_name: 마구리 505*355
specification: 505*355
is_sellable: 1, is_purchasable: 1, is_producible: 0

4.4 Phase 1.4: BOM 관계 구조

4.4.1 SAM BOM 구조

FG 품목의 bom JSON 형태:

// FG-KSE01-벽면형-EGI (스크린, bom_items: 3)
[
    {"quantity": 2, "child_item_id": 13170},  // PT-가이드레일
    {"quantity": 1, "child_item_id": 13174},  // PT-하단마감재
    {"quantity": 2, "child_item_id": 13175}   // PT-L-BAR
]

BOM 패턴 요약:

대분류 FG 품목 수 BOM 구성
스크린 (KSS01/KSE01/KWE01/KSS02) 12 PT 3개 (가이드레일×2 + 하단마감재×1 + L-BAR×2)
철재 (KQTS01/KTE01) 6 PT 2개 (가이드레일×2 + 하단마감재×1)

4.4.2 5130 레거시 구조 비교

5130 models (18개 활성):

모델명 대분류 마감 유형 가이드레일
KSS01 스크린 SUS마감 벽면형/측면형
KSE01 스크린 SUS마감/EGI마감 벽면형/측면형
KWE01 스크린 SUS마감/EGI마감 벽면형/측면형
KQTS01 철재 SUS마감 벽면형/측면형
KTE01 철재 SUS마감/EGI마감 벽면형/측면형
KSS02 스크린 SUS마감 벽면형/측면형

5130 BDmodels (59개 활성):

model_name 건수 설명
KSS01 4 가이드레일/하단마감재/L-BAR 등
KSE01 8
KWE01 7
KQTS01 3
KTE01 6
KSS02 4
KDSS01 4
(빈값) 23 공용 부품

4.4.3 견적 의존성 분석

FormulaEvaluatorService가 의존하는 데이터:

  1. items.bom JSON → child_item_id로 PT 품목 조회 → PT의 item_categoryCategoryGroup 매핑
  2. items.code → 품목 식별에 사용
  3. items.item_category → 카테고리 그룹 가격 산출에 사용

⚠️ 수정 금지 영역:

  • items.bom JSON 구조 ([{child_item_id, quantity}])
  • items.code 체계 (FG-모델명-가이드레일-마감, PT-부품명)
  • items.item_category 값 (스크린, 철재)
  • FormulaEvaluatorService 로직

안전한 수정 영역:

  • item_pages/item_sections/item_fields (폼 표시 설정)
  • entity_relationships (폼 구성 관계)
  • item_fields.options (드롭다운 선택 값)
  • item_details (표시용 상세 정보)
  • items.attributes JSON (프론트엔드 표시용, 견적 미사용)

5. Phase 2 수정 계획

5.1 FG(제품) 필드 설정 정비

현재 문제: FG의 attributes 키(model_name, finishing_type, guiderail_type, major_category)와 FG page의 item_fields field_key가 매핑되지 않음

수정 방안:

순서 작업 field_key field_type options
1 모델명 필드 추가/수정 model_name dropdown KSS01, KSE01, KWE01, KQTS01, KTE01, KSS02
2 대분류 필드 추가 major_category dropdown 스크린, 철재
3 마감유형 필드 추가 finishing_type dropdown SUS마감, EGI마감
4 설치유형 필드 추가 guiderail_type dropdown 벽면형, 측면형
5 기존 필드 유지 139_productName → 상품명 textbox -
6 기존 필드 유지 141_lotNum → 로트 약자 textbox -
7 인정 관련 필드 유지 142~145_* textbox/date -

storage_type 설정: json (attributes JSON에서 읽기)

5.2 PT(부품) 필드 설정 정비

현재 문제: 빈 field_key 필드 존재, 부품유형별 조건부 필드가 복잡

수정 방안:

  • 빈 field_key 필드 수정 또는 비활성화
  • Part_type 드롭다운 options를 실제 부품 유형으로 갱신
  • 부품유형별 display_condition JSON 설정으로 조건부 표시

5.3 RM/SM/CS 필드 설정 정비

현재 문제: 드롭다운 options가 플레이스홀더 값

수정 방안:

  • RM: 100_item_name options → 실제 원자재명 (철판, 알루미늄, 스테인리스, 아연도금강판 등)
  • RM: 101~104_specification_* options → 실제 규격 값으로 교체
  • SM: 107_item_name options → 실제 부자재명
  • SM: 108~109_specification_* options → 실제 규격 값

5.4 FG item_details 데이터 보완

현재 문제: FG 18개 품목의 item_details 레코드 없음

수정 방안: FG 18개 품목에 대해 item_details 생성

item_id: (각 FG item id)
is_sellable: 1
is_purchasable: 0
is_producible: 1
product_category: (스크린/철재)
item_name: (SAM name)
specification: (마감유형-가이드레일유형)

5.5 드롭다운 options 실데이터 매핑

5130 데이터 기반으로 매핑할 값:

필드 현재 options 목표 options
FG model_name 없음 KSS01, KSE01, KWE01, KQTS01, KTE01, KSS02
FG major_category 없음 스크린, 철재
FG finishing_type 없음 SUS마감, EGI마감
FG guiderail_type 없음 벽면형, 측면형
PT Part_type 확인 필요 조립부품, 벤딩부품, 구매부품, BD부품
RM 100_item_name 기존값 유지 철판, 알루미늄, 스테인리스, 아연도금강판
RM 규격 101~104 옵션1-1 등 (임시값) 실제 규격 값으로 교체 필요

5.6 고정컬럼-동적필드 섀도잉 정리

상세 분석: 섹션 4.2.3 참조

5.6.1 is_active 중복 정리 (⚠️ 컨펌 필요)

목표: items.is_active 고정 컬럼만으로 활성/비활성 상태를 관리하도록 통합

방안 A (권장): 동적 필드를 is_common=1 공통필드(id:163)로 교체

각 page에서 중복 동적 필드를 제거하고, 공통 필드 is_active(id:163)를 entity_relationship으로 연결:

대상 page 제거할 동적 필드 대체 작업 내용
SM (id:1017) id:164 (field_163) id:163 (is_active) 1) section(id:94)→field(id:164) 관계 삭제 2) section(id:94)→field(id:163) 관계 추가
PT 측면규격 (id:99) id:105 (105_state) id:163 (is_active) 1) section(id:99)→field(id:105) 관계 삭제 2) section(id:99)→field(id:163) 관계 추가
PT 측면규격 (id:99) id:133 (133_state) id:163 (is_active) 1) section(id:99)→field(id:133) 관계 삭제 (id:163 이미 추가됨)
PT 기본정보 (id:95) id:138 (138_state) id:163 (is_active) 1) section(id:95)→field(id:138) 관계 삭제 2) section(id:95)→field(id:163) 관계 추가
FG 기본정보 (id:102) id:138 (138_state) id:163 (is_active) 1) section(id:102)→field(id:138) 관계 삭제 2) section(id:102)→field(id:163) 관계 추가
PT 기본정보 (id:95) id:152 (null key) id:163 (is_active) 1) section(id:95)→field(id:152) 관계 삭제 (id:163 이미 추가됨)

추가 작업:

  • 제거된 동적 필드(id:105,131,133,138,152,164)는 is_active=0으로 비활성화 (삭제 대신 비활성화하여 안전)
  • 기존 items.attributes JSON에 105_state, 138_state 등의 키로 저장된 값이 있다면, 해당 값을 items.is_active 컬럼과 동기화 필요 여부 확인

방안 B (보수적): 동적 필드의 field_key를 is_active로 변경만

동적 필드를 유지하되, source_columnis_active로, storage_typecolumn으로 변경하여 같은 컬럼을 가리키게 함. 관계 변경 없이 안전하지만, 불필요한 필드가 잔존함.

실행 전 확인 사항:

-- 동적 필드에 실제 데이터가 저장되어 있는지 확인
SELECT id, code, name,
  JSON_EXTRACT(attributes, '$.105_state') as s105,
  JSON_EXTRACT(attributes, '$.131_state') as s131,
  JSON_EXTRACT(attributes, '$.133_state') as s133,
  JSON_EXTRACT(attributes, '$.138_state') as s138,
  JSON_EXTRACT(attributes, '$.field_163') as f163
FROM items
WHERE tenant_id = 287 AND deleted_at IS NULL
AND (
  JSON_EXTRACT(attributes, '$.105_state') IS NOT NULL
  OR JSON_EXTRACT(attributes, '$.131_state') IS NOT NULL
  OR JSON_EXTRACT(attributes, '$.133_state') IS NOT NULL
  OR JSON_EXTRACT(attributes, '$.138_state') IS NOT NULL
  OR JSON_EXTRACT(attributes, '$.field_163') IS NOT NULL
);

5.6.2 null key 필드 비활성화 ( 즉시 가능)

-- item_fields id:152 (field_key=NULL, 품목상태, PT page)
-- key가 없어서 데이터 매핑 불가. 비활성화 처리.
UPDATE item_fields SET is_active = 0 WHERE id = 152 AND tenant_id = 287;

5.6.3 미연결 필드 비활성화 ( 즉시 가능)

entity_relationship에 연결되지 않아 어떤 폼에도 표시되지 않는 필드:

-- 미연결 필드 5건 비활성화
UPDATE item_fields SET is_active = 0
WHERE id IN (116, 117, 129, 131, 136) AND tenant_id = 287;

-- 확인: 이 필드들이 실제 미연결인지 재검증
SELECT f.id, f.field_key, f.field_name, er.id as rel_id
FROM item_fields f
LEFT JOIN entity_relationships er
  ON er.child_type = 'field' AND er.child_id = f.id AND er.tenant_id = 287
WHERE f.id IN (116, 117, 129, 131, 136) AND f.tenant_id = 287;
-- rel_id가 모두 NULL이면 확실히 미연결
field id field_key 비활성화 이유
116 116_bending_parts 미연결. id:122(122_bending_parts)와 중복
117 117_purchase_parts 미연결. id:132(132_PurchasedItemName)와 중복
129 unit_2 미연결. id:98(unit)과 중복
131 131_state 미연결. is_active 중복
136 unit_3 미연결. id:98(unit)과 중복

5.6.4 다음에 정리할 항목 (이번 범위 밖)

유형 건수 다음에 정리하는 이유
name (품목명) 중복 8건 PT 부품유형별 분기 UI(조립부품명/벤딩부품명/구매부품명)와 맞물림. display_condition 기반 렌더링 로직 변경 필요
unit (단위) 중복 2건 (활성) id:98이 4개 page에서 사용 중. 공통필드(id:156)와의 역할 분담 정책 결정 필요
specification (규격) 중복 6건 원자재 4단 규격은 의도된 설계. item_details.specification과의 동기화 정책 필요
description (비고) 중복 4건 note1/note2/note3 용도별 분리가 의도일 수 있음
certification_* 중복 3건 FG item_details 생성(5.4) 후 연계 검토
part_type 중복 1건 PT에서 정상 사용 중

6. 컨펌 대기 목록

# 항목 변경 내용 영향 범위 상태
1 FG 필드 추가 4개 필드 추가(id:177-180) + SM/RM options 추가 item_fields, entity_relationships 완료
2 category_id 분류 categories 5건 추가, 780건 매핑 categories, items 완료
3 FG item_details 생성 18건 INSERT 완료 (Phase 2B-4) item_details 완료
4 PT/SM/RM attributes 매핑 field_key ↔ attributes JSON 키 정합성 완료 (Phase 2B-5) item_fields, items.attributes 완료
5 견적 시스템 영향 검증 KyungdongFormulaHandler가 items.attributes 미참조 확인. 견적 영향 없음 FormulaEvaluatorService 완료
6 SM/CS 프론트엔드 검증 SM: display_condition 수정 후 정상. CS: 무형상품이라 실질 영향 없음 dev.sam.kr 완료
7 RM/SM display_condition 수정 RM id:100 + SM id:107 조건부 표시 매핑 추가 item_fields 완료
8 섀도잉 정리 (재수행) Phase 2A에서 롤백됨. display_condition 안전 확인 후 재수행 entity_relationships, item_fields 대기
9 SM field 108/109 드롭다운 옵션 정비 현재 테스트 데이터(부자재1-1 등) → 실제 규격값으로 교체 필요 item_fields.options 대기

7. 변경 이력

날짜 항목 변경 내용 파일 승인
2026-01-31 - 문서 초안 작성 및 Phase 1 분석 완료 - -
2026-01-31 4.2.3 고정컬럼-동적필드 섀도잉 분석 추가 (is_active 6건, null key 1건, 미연결 5건) - -
2026-01-31 5.6 Phase 2에 섀도잉 정리 작업(2.6) 추가. 구체적 SQL, field id, entity_relationship 변경 계획 명시 - -
2026-01-31 2.6 Phase 2.6 실행 완료: null key(id:152) 비활성화, 미연결 5건 비활성화, is_active 중복 통합 - → 롤백
2026-01-31 2.1~2.5 Phase 2A 전체 실행 완료 (FG 필드, PT options, RM/SM options, item_details, 섀도잉 정리) - → 롤백
2026-01-31 - ⚠️ DB 복원 (전체 롤백): PT Part_type display_condition 깨짐 발견. 백업에서 DB 복원하여 Phase 2A 전체 롤백 samdb 전체 롤백
2026-01-31 - 접근 방식 변경: 설정 변경 → 데이터 우선 정비로 전환. 기존 설정 교체 금지, 추가만 허용 - -
2026-01-31 2B-1 FG 필드 4개 재추가(id:177-180), section 102 연결. SM id:107 기존 옵션 유지 + 11종 추가. RM id:100-104 기존 옵션 유지 + 실데이터 추가 item_fields, entity_relationships
2026-01-31 2B-2 BOM 확인: FG 18건 모두 BOM 정상 구성됨 (스크린 3개 PT, 철재 2개 PT) items.bom
2026-01-31 2B-3 category_id 분류: categories 5건 추가(RAW_MATERIAL:298, FABRIC:299, SERVICE:300, GASKET:301, MISC_PART:302). 780건 전체 category_id 매핑 (RM→298, SM→217, CS→300, FG→214, PT→패턴매칭) categories, items
2026-01-31 2B-4 FG item_details 18건 생성(id:524-541). is_sellable=1, is_producible=1, product_category(스크린/철재), item_name, specification(마감유형-설치유형) item_details
2026-01-31 2B-5 attributes field_key 매핑: PT Part_type 669건(조립400/구매205/절곡64), RM 100~103 field_key 28건(SUS/EGI/원단류+규격파싱), SM 107 카테고리 61건+spec→108, CS item_name 4건 items.attributes
2026-01-31 2B-검증 프론트엔드 검증: FG(모델명/대분류/마감유형/설치유형 ), PT(Part_type→조건부필드 ), RM(품목명 , 규격 display_condition 불일치 발견) -
2026-01-31 2B-DC RM 필드 100 display_condition 수정: "SUS(스테인리스)"→[101,102,103], "EGI(아연도금강판)"→[101,102,103], "원단류"→[101] 추가. 기존 4개 조건 유지 item_fields.id=100
2026-02-03 견적검증 견적 시스템 영향 검증 완료. KyungdongFormulaHandler(tenant_id=287)는 items.attributes 미참조. quote_items.item_id=NULL(스냅샷 저장). Phase 2B 변경이 견적 계산에 영향 없음 확인 FormulaEvaluatorService, KyungdongFormulaHandler
2026-02-03 SM검증 SM 프론트엔드 검증: 알카바(id:12565) 편집 화면에서 품목명 표시, 규격 미표시 (display_condition에 "알카바" 매핑 누락). field 108/109 드롭다운 옵션은 테스트 데이터(부자재1-1 등) dev.sam.kr 프론트엔드
2026-02-03 CS검증 CS 프론트엔드 검증: 출장비(id:12860) 편집 화면에서 품목명 , 규격(사양) 빈칸 (field_key=specification vs attributes.spec 불일치, 무형상품이라 실질 영향 없음) dev.sam.kr 프론트엔드
2026-02-03 SM-DC SM 필드 107 display_condition 수정: 기존 2개(육각볼트→108, 썬더볼트→109) + 8개 추가(샤우드/앵글/알카바/컨트롤박스/기타/포장자재/방범부품/원단류→108). 알카바 편집 화면에서 규격 필드 표시 확인 item_fields.id=107

8. 참고 문서

  • DB 스키마: docs/specs/database-schema.md
  • 품목 정책: docs/rules/item-policy.md
  • 품질 체크리스트: docs/standards/quality-checklist.md
  • 빠른 시작: docs/quickstart/quick-start.md
  • API 규칙: docs/standards/api-rules.md
  • 기존 이관 계획: docs/plans/items-migration-kyungdong-plan.md
  • MNG 필드 관리 계획: docs/plans/mng-item-field-management-plan.md

9. 새 세션 작업 시작 가이드

9.0 이 문서만으로 작업을 시작하는 방법

1단계: 현재 상태 확인

  • 이 문서의 "📍 현재 진행 상태" 섹션에서 마지막 완료 작업과 다음 작업 확인
  • Phase 2 대상 범위(섹션 2.2) 테이블에서 / 상태 확인

2단계: 환경 확인

# Docker 컨테이너 실행 확인
docker ps | grep sam

# 테넌트 데이터 접근 확인 (tenant_id=287)
docker exec sam-api-1 php artisan tinker --execute="echo DB::table('items')->where('tenant_id', 287)->count();"
# 기대값: 780

3단계: 작업 실행 순서 (Phase 2)

┌─────────────────────────────────────────────────────────────────┐
│  Phase 2 실행 순서 (권장)                                         │
├─────────────────────────────────────────────────────────────────┤
│                                                                  │
│  2.6 섀도잉 정리 (안전, 선행 작업)                                │
│   ├─ 5.6.2 null key 비활성화 (즉시 가능)                         │
│   ├─ 5.6.3 미연결 필드 비활성화 (즉시 가능)                      │
│   └─ 5.6.1 is_active 중복 통합 (⚠️ 컨펌 필요)                   │
│       └─ 사전: 5.6.1 확인 SQL 실행하여 기존 데이터 유무 확인     │
│                                                                  │
│  2.1 FG 필드 설정 정비 (⚠️ 컨펌 필요)                            │
│   └─ 섹션 5.1 참조: 4개 필드 추가 + entity_relationship 연결     │
│                                                                  │
│  2.2 PT 필드 설정 정비 (⚠️ 컨펌 필요)                            │
│   └─ 섹션 5.2 참조                                               │
│                                                                  │
│  2.3 SM/RM/CS 필드 설정 정비                                      │
│   └─ 섹션 5.3 참조                                               │
│                                                                  │
│  2.5 드롭다운 options 실데이터 매핑                               │
│   └─ 섹션 5.5 참조: FG 4개 + PT/RM 교체                         │
│                                                                  │
│  2.4 FG item_details 데이터 보완                                  │
│   └─ 섹션 5.4 참조: 18건 INSERT                                  │
│                                                                  │
│  검증                                                             │
│   └─ 섹션 10 테스트 케이스 실행                                   │
│                                                                  │
└─────────────────────────────────────────────────────────────────┘

4단계: 작업 대상 테이블/ID 빠른 참조

테이블 tenant_id 주요 ID 범위 용도
item_pages 287 1015~1019 (CS/RM/SM/PT/FG) 품목유형별 폼
item_sections 287 92~102 섹션 그룹
item_fields 287 96~164 필드 정의
entity_relationships 287 page→section 26건, section→field 66건 계층 연결
items 287 13147~13164 (FG 18건) 품목 데이터
item_details - PT 129건, FG 0건 품목 상세

5단계: 수정 금지 영역 (반드시 확인)

  • items.bom JSON 구조 변경 금지
  • items.code 체계 변경 금지
  • items.item_category 값 변경 금지
  • FormulaEvaluatorService 수정 금지
  • 위 항목은 견적 로직에 직접 영향. 상세: 섹션 4.4.3

10. Serena 메모리 관리 정책

10.1 세션 시작 시 (Load Strategy)

read_memory("item-data-alignment-state")     // 1. 상태 파악
read_memory("item-data-alignment-snapshot")  // 2. 사고 흐름 복구
read_memory("item-data-alignment-active-symbols") // 3. 작업 대상 파악

10.2 작업 중 관리 (Context Defense)

컨텍스트 잔량 Action 내용
30% 이하 Snapshot write_memory("item-data-alignment-snapshot", "코드변경+논의요약")
20% 이하 Context Purge write_memory("item-data-alignment-active-symbols", "주요 수정 파일/함수")
10% 이하 Stop & Save 최종 상태 저장 후 세션 교체 권고

10.3 Serena 메모리 구조

  • item-data-alignment-state: { phase, progress, next_step, last_decision } (JSON 구조)
  • item-data-alignment-snapshot: 현재까지의 논의 및 코드 변경점 요약 (Text)
  • item-data-alignment-rules: 견적 영향 금지 등 불변 규칙 (Text)
  • item-data-alignment-active-symbols: 현재 수정 중인 파일/심볼 리스트 (List)

11. 검증 결과

작업 완료 후 이 섹션에 검증 결과 추가

11.1 테스트 케이스

입력값 예상 결과 실제 결과 상태
FG-KSE01-벽면형-EGI 조회 model_name=KSE01, finishing_type=EGI마감 등 표시 상세 뷰는 고정 레이아웃, 품목기준관리 설정에서 필드 4개 정상 등록 확인 ⚠️ 부분
PT-가이드레일 조회 base_price, 부품유형 등 표시 품목기준관리에서 Part_type 4종 options 확인
FG BOM 표시 가이드레일×2, 하단마감재×1, L-BAR×2 표시 상세 화면에서 BOM 3건 정확히 표시
견적 생성 (수정 후) 기존과 동일한 견적 금액 산출 KyungdongFormulaHandler 분석: items.attributes 미참조. quote_items.item_id=ALL NULL(스냅샷). Phase 2B 변경 영향 없음 확인
SM 알카바 규격 표시 품목명 "알카바" 선택 시 규격(field 108) 표시 display_condition 수정 후 규격 필드 표시 . 드롭다운 옵션은 테스트 데이터(별도 정비 필요)
CS 출장비 편집 품목명/규격 필드 표시 품목명 , 규격(사양) 빈칸(field_key=specification vs attributes.spec, 무형상품이라 실질 영향 없음)
SM 품목 활성 여부 items.is_active 컬럼 값 표시 (field_163 아님) 품목기준관리에서 id:163 공통필드로 교체 확인, id:164 제거
PT 품목상태 필드 items.is_active 공통 필드로 통합 표시 기본정보/측면규격 양쪽에 id:163 연결 확인, id:105/133/138/152 제거
FG 품목상태 필드 items.is_active 공통 필드로 통합 표시 기본정보에 id:163 연결 확인, id:138 제거
id:152 (null key) 폼에 표시되지 않음 (비활성화) PT 기본정보에서 미표시 확인
미연결 필드 5건 폼에 표시되지 않음 (비활성화) 모든 페이지에서 미표시 확인 (id:116,117은 고아 section에 연결 상태)

11.2 성공 기준 달성 현황

기준 달성 비고
FG 18개 품목이 모든 필드 정상 표시 ⚠️ DB 설정 완료. 상세 뷰는 고정 레이아웃이라 동적 필드 미표시 (프론트 별도)
PT 부품유형별 조건부 필드 정상 작동 Part_type 4종 options 갱신 완료
RM/SM 드롭다운 실제 값 표시 RM 재질/두께/폭/길이, SM 11개 카테고리 반영 확인
견적 금액 변동 없음 (회귀 테스트) KyungdongFormulaHandler 코드 분석 + quote_items 스냅샷 구조 확인. Phase 2B 영향 없음
SM display_condition 정상 작동 field 107에 10개 품목명→규격필드 매핑 완료. 알카바 편집 화면에서 규격 표시 확인
CS 프론트엔드 정상 무형상품(출장비/노무비 등) 편집 화면 정상. 규격 미매핑은 실질 영향 없음
품목 목록 → 상세 → 문서 데이터 흐름 정상 FG 목록 18건 표시, BOM 3건 정상
is_active 중복 필드 통합 완료 (6건 → 공통필드 1개) SM/PT/FG 모두 id:163으로 교체 확인
null key 필드(id:152) 비활성화 폼에서 미표시 확인
미연결 필드(id:116,117,129,131,136) 비활성화 폼에서 미표시 확인

12. 자기완결성 점검 결과

12.1 체크리스트 검증

# 검증 항목 상태 비고
1 작업 목적이 명확한가? 섹션 1.1 배경
2 성공 기준이 정의되어 있는가? 섹션 11.2
3 작업 범위가 구체적인가? 섹션 2 대상 범위
4 의존성이 명시되어 있는가? 견적 금지 영역 명시 (4.4.3), 수정금지 (9.0 5단계)
5 참고 파일 경로가 정확한가? 섹션 8
6 단계별 절차가 실행 가능한가? 섹션 9.0 (새 세션 가이드), 섹션 5 (상세 수정 계획)
7 검증 방법이 명시되어 있는가? 섹션 11.1
8 모호한 표현이 없는가? 구체적 테이블/필드/ID, SQL 쿼리 명시

12.2 새 세션 시뮬레이션 테스트

질문 답변 가능 참조 섹션
Q1. 이 작업의 목적은 무엇인가? 1.1 배경
Q2. 어디서부터 시작해야 하는가? 9.0 3단계 (실행 순서 다이어그램)
Q3. 어떤 데이터를 수정해야 하는가? 5.1~5.6 (상세 수정 계획 + SQL)
Q4. 절대 건드리면 안 되는 것은? 9.0 5단계 + 4.4.3 (수정 금지 영역)
Q5. 작업 완료 확인 방법은? 11.1 테스트 케이스, 11.2 성공 기준
Q6. 막혔을 때 참고 문서는? 8. 참고 문서
Q7. DB 접속/환경 세팅은? 9.0 2단계 (환경 확인 명령어)
Q8. 테이블/ID 범위는? 9.0 4단계 (빠른 참조 테이블)

결과: 8/8 통과 → 자기완결성 확보


이 문서는 /sc:plan 스킬로 생성되었습니다.