Files
sam-react-prod/src/types/master-data.ts
byeongcheolryu 63f5df7d7d feat: 품목 관리 및 마스터 데이터 관리 시스템 구현
주요 기능:
- 품목 CRUD 기능 (생성, 조회, 수정)
- 품목 마스터 데이터 관리 시스템
- BOM(Bill of Materials) 관리 기능
- 도면 캔버스 기능
- 품목 속성 및 카테고리 관리
- 스크린 인쇄 생산 관리 페이지

기술 개선:
- localStorage SSR 호환성 수정 (9개 useState 초기화)
- Shadcn UI 컴포넌트 추가 (table, tabs, alert, drawer 등)
- DataContext 및 DeveloperModeContext 추가
- API 라우트 구현 (items, master-data)
- 타입 정의 및 유틸리티 함수 추가

빌드 테스트:  성공 (3.1초)

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-11-18 14:17:52 +09:00

283 lines
6.3 KiB
TypeScript

/**
* 품목기준관리 타입 정의
*
* 동적 페이지 구성, 버전 관리, 멀티테넌시 지원
*/
import type { ItemType } from './item';
// ===== 페이지 타입 =====
/**
* 페이지 유형
* - item-master: 품목기준정보
* - quotation: 견적
* - sales-order: 수주
* - formula: 계산식
* - pricing: 단가
*/
export type PageType = 'item-master' | 'quotation' | 'sales-order' | 'formula' | 'pricing';
/**
* 필드 입력 타입
*/
export type FieldInputType =
| 'textbox'
| 'dropdown'
| 'checkbox'
| 'number'
| 'date'
| 'textarea'
| 'file'
| 'multi-column';
/**
* 섹션 타입
*/
export type SectionType = 'fields' | 'bom' | 'table';
// ===== 필드 설정 =====
/**
* 필드 표시 조건
*/
export interface FieldDisplayCondition {
dependsOn: string; // 의존하는 필드 키
showWhen?: string | string[]; // 표시 조건 값
hideWhen?: string | string[]; // 숨김 조건 값
}
/**
* 필드 유효성 검사 규칙
*/
export interface FieldValidationRule {
type: 'required' | 'min' | 'max' | 'pattern' | 'custom';
value?: any;
message: string;
}
/**
* 필드 속성
*/
export interface FieldProperty {
inputType: FieldInputType;
required: boolean;
row: number; // 그리드 행 번호
col: number; // 그리드 열 번호
options?: string[]; // 드롭다운 옵션
defaultValue?: any;
placeholder?: string;
// 멀티컬럼 필드 관련
multiColumn?: boolean;
columnCount?: number;
columnNames?: string[];
// 유효성 검사
validation?: FieldValidationRule[];
// 표시 조건
displayCondition?: FieldDisplayCondition;
}
/**
* 필드 정의
*/
export interface FieldConfig {
id: string;
name: string; // 필드 라벨
fieldKey: string; // 데이터 키
property: FieldProperty;
helpText?: string; // 도움말 텍스트
}
// ===== 섹션 설정 =====
/**
* 섹션 정의
*/
export interface SectionConfig {
id: string;
title: string; // 섹션 제목
description?: string;
type: SectionType;
fields: FieldConfig[];
order: number; // 섹션 순서
isCollapsible: boolean; // 접기/펼치기 가능 여부
isCollapsed: boolean; // 기본 접힘 상태
// 조건부 표시
category?: string[]; // 특정 카테고리에서만 표시
}
// ===== 페이지 설정 =====
/**
* 페이지 구성 정보
*/
export interface PageConfig {
id: string;
pageName: string; // 페이지명
pageType: PageType; // 페이지 유형
itemType?: ItemType; // 연결된 품목 유형 (optional)
sections: SectionConfig[]; // 섹션 목록
isActive: boolean; // 사용 여부
// 버전 관리
version: number; // 현재 버전
isFinal: boolean; // 최종 확정 여부
// 멀티테넌시
tenantId: string; // 테넌트 ID
// 메타데이터
createdAt: string;
updatedAt: string;
createdBy: string;
updatedBy?: string;
}
// ===== 버전 관리 =====
/**
* 페이지 구성 변경 이력
*/
export interface PageConfigRevision {
id: string;
pageConfigId: string;
version: number; // 버전 번호
previousVersion: number; // 이전 버전
changes: PageConfigChange[]; // 변경 내역
snapshot: PageConfig; // 전체 스냅샷
// 변경 정보
changedAt: string;
changedBy: string;
changeReason?: string;
// 승인 정보
isApproved: boolean;
approvedAt?: string;
approvedBy?: string;
}
/**
* 페이지 구성 변경 상세
*/
export interface PageConfigChange {
type: 'field_added' | 'field_removed' | 'field_modified' | 'section_added' | 'section_removed' | 'section_modified';
targetId: string; // 변경된 필드/섹션 ID
fieldName?: string; // 변경된 항목명
oldValue?: any;
newValue?: any;
description: string;
}
// ===== 데이터 입력 =====
/**
* 동적 폼 데이터
*/
export interface DynamicFormData {
id?: string;
pageConfigId: string;
pageType: PageType;
tenantId: string;
// 동적 필드 데이터 (key-value)
fieldData: Record<string, any>;
// 버전 관리
version: number;
isFinal: boolean;
// 메타데이터
createdAt?: string;
updatedAt?: string;
createdBy?: string;
updatedBy?: string;
}
// ===== API 응답 =====
/**
* API 응답 기본 구조
*/
export interface MasterDataApiResponse<T> {
success: boolean;
data: T;
message?: string;
errors?: Record<string, string[]>;
}
/**
* 페이지네이션 응답
*/
export interface MasterDataPaginatedResponse<T> {
data: T[];
current_page: number;
last_page: number;
per_page: number;
total: number;
}
/**
* 페이지 구성 조회 파라미터
*/
export interface FetchPageConfigParams {
pageType?: PageType;
itemType?: ItemType;
isActive?: boolean;
version?: number;
}
/**
* 버전 비교 결과
*/
export interface VersionComparisonResult {
version1: number;
version2: number;
changes: PageConfigChange[];
addedFields: FieldConfig[];
removedFields: FieldConfig[];
modifiedFields: Array<{
field: FieldConfig;
changes: Record<string, { old: any; new: any }>;
}>;
}
// ===== 유틸리티 타입 =====
/**
* 페이지 타입 라벨
*/
export const PAGE_TYPE_LABELS: Record<PageType, string> = {
'item-master': '품목기준정보',
'quotation': '견적',
'sales-order': '수주',
'formula': '계산식',
'pricing': '단가',
} as const;
/**
* 섹션 타입 라벨
*/
export const SECTION_TYPE_LABELS: Record<SectionType, string> = {
'fields': '입력 필드',
'bom': '부품구성표',
'table': '테이블',
} as const;
/**
* 필드 입력 타입 라벨
*/
export const FIELD_INPUT_TYPE_LABELS: Record<FieldInputType, string> = {
'textbox': '텍스트 입력',
'dropdown': '드롭다운',
'checkbox': '체크박스',
'number': '숫자 입력',
'date': '날짜',
'textarea': '텍스트 영역',
'file': '파일',
'multi-column': '다중 컬럼',
} as const;