380 lines
8.0 KiB
TypeScript
380 lines
8.0 KiB
TypeScript
/**
|
|
* 화면 임베딩 및 데이터 전달 시스템 타입 정의
|
|
*/
|
|
|
|
// ============================================
|
|
// 1. 화면 임베딩 타입
|
|
// ============================================
|
|
|
|
/**
|
|
* 임베딩 모드
|
|
*/
|
|
export type EmbeddingMode =
|
|
| "view" // 읽기 전용
|
|
| "select" // 선택 모드 (체크박스)
|
|
| "form" // 폼 입력 모드
|
|
| "edit"; // 편집 모드
|
|
|
|
/**
|
|
* 임베딩 위치
|
|
*/
|
|
export type EmbeddingPosition =
|
|
| "left"
|
|
| "right"
|
|
| "top"
|
|
| "bottom"
|
|
| "center";
|
|
|
|
/**
|
|
* 임베딩 설정
|
|
*/
|
|
export interface EmbeddingConfig {
|
|
width?: string; // "50%", "400px"
|
|
height?: string; // "100%", "600px"
|
|
resizable?: boolean;
|
|
multiSelect?: boolean;
|
|
showToolbar?: boolean;
|
|
showSearch?: boolean;
|
|
showPagination?: boolean;
|
|
}
|
|
|
|
/**
|
|
* 화면 임베딩
|
|
*/
|
|
export interface ScreenEmbedding {
|
|
id: number;
|
|
parentScreenId: number;
|
|
childScreenId: number;
|
|
position: EmbeddingPosition;
|
|
mode: EmbeddingMode;
|
|
config: EmbeddingConfig;
|
|
companyCode: string;
|
|
createdAt: string;
|
|
updatedAt: string;
|
|
createdBy?: string;
|
|
}
|
|
|
|
// ============================================
|
|
// 2. 데이터 전달 타입
|
|
// ============================================
|
|
|
|
/**
|
|
* 컴포넌트 타입
|
|
*/
|
|
export type ComponentType =
|
|
| "table" // 테이블
|
|
| "input" // 입력 필드
|
|
| "select" // 셀렉트 박스
|
|
| "textarea" // 텍스트 영역
|
|
| "checkbox" // 체크박스
|
|
| "radio" // 라디오 버튼
|
|
| "date" // 날짜 선택
|
|
| "repeater" // 리피터 (반복 그룹)
|
|
| "form-group" // 폼 그룹
|
|
| "hidden"; // 히든 필드
|
|
|
|
/**
|
|
* 데이터 수신 모드
|
|
*/
|
|
export type DataReceiveMode =
|
|
| "append" // 기존 데이터에 추가
|
|
| "replace" // 기존 데이터 덮어쓰기
|
|
| "merge"; // 기존 데이터와 병합 (키 기준)
|
|
|
|
/**
|
|
* 변환 함수
|
|
*/
|
|
export type TransformFunction =
|
|
| "none" // 변환 없음
|
|
| "sum" // 합계
|
|
| "average" // 평균
|
|
| "count" // 개수
|
|
| "min" // 최소값
|
|
| "max" // 최대값
|
|
| "first" // 첫 번째 값
|
|
| "last" // 마지막 값
|
|
| "concat" // 문자열 결합
|
|
| "join" // 배열 결합
|
|
| "custom"; // 커스텀 함수
|
|
|
|
/**
|
|
* 조건 연산자
|
|
*/
|
|
export type ConditionOperator =
|
|
| "equals"
|
|
| "notEquals"
|
|
| "contains"
|
|
| "notContains"
|
|
| "greaterThan"
|
|
| "lessThan"
|
|
| "greaterThanOrEqual"
|
|
| "lessThanOrEqual"
|
|
| "in"
|
|
| "notIn";
|
|
|
|
/**
|
|
* 매핑 규칙
|
|
*/
|
|
export interface MappingRule {
|
|
sourceField: string; // 소스 필드명
|
|
targetField: string; // 타겟 필드명
|
|
transform?: TransformFunction; // 변환 함수
|
|
transformConfig?: any; // 변환 함수 설정
|
|
defaultValue?: any; // 기본값
|
|
required?: boolean; // 필수 여부
|
|
}
|
|
|
|
/**
|
|
* 조건
|
|
*/
|
|
export interface Condition {
|
|
field: string;
|
|
operator: ConditionOperator;
|
|
value: any;
|
|
}
|
|
|
|
/**
|
|
* 검증 설정
|
|
*/
|
|
export interface ValidationConfig {
|
|
required?: boolean;
|
|
minRows?: number;
|
|
maxRows?: number;
|
|
customValidation?: string; // JavaScript 함수 문자열
|
|
}
|
|
|
|
/**
|
|
* 데이터 수신자
|
|
*/
|
|
export interface DataReceiver {
|
|
targetComponentId: string; // 타겟 컴포넌트 ID
|
|
targetComponentType: ComponentType;
|
|
mode: DataReceiveMode;
|
|
mappingRules: MappingRule[];
|
|
condition?: Condition; // 조건부 전달
|
|
validation?: ValidationConfig;
|
|
}
|
|
|
|
/**
|
|
* 버튼 검증 설정
|
|
*/
|
|
export interface ButtonValidation {
|
|
requireSelection: boolean;
|
|
minSelection?: number;
|
|
maxSelection?: number;
|
|
confirmMessage?: string;
|
|
customValidation?: string;
|
|
}
|
|
|
|
/**
|
|
* 전달 버튼 설정
|
|
*/
|
|
export interface TransferButtonConfig {
|
|
label: string;
|
|
position: "left" | "right" | "center";
|
|
icon?: string;
|
|
variant?: "default" | "outline" | "ghost" | "destructive";
|
|
size?: "sm" | "default" | "lg";
|
|
validation?: ButtonValidation;
|
|
clearAfterTransfer?: boolean;
|
|
}
|
|
|
|
/**
|
|
* 데이터 전달 설정
|
|
*/
|
|
export interface ScreenDataTransfer {
|
|
id: number;
|
|
sourceScreenId: number;
|
|
targetScreenId: number;
|
|
sourceComponentId?: string;
|
|
sourceComponentType?: string;
|
|
dataReceivers: DataReceiver[];
|
|
buttonConfig: TransferButtonConfig;
|
|
companyCode: string;
|
|
createdAt: string;
|
|
updatedAt: string;
|
|
createdBy?: string;
|
|
}
|
|
|
|
// ============================================
|
|
// 3. 분할 패널 타입
|
|
// ============================================
|
|
|
|
/**
|
|
* 레이아웃 설정
|
|
*/
|
|
export interface LayoutConfig {
|
|
splitRatio: number; // 0-100 (좌측 비율)
|
|
resizable: boolean;
|
|
minLeftWidth?: number; // 최소 좌측 너비 (px)
|
|
minRightWidth?: number; // 최소 우측 너비 (px)
|
|
orientation: "horizontal" | "vertical";
|
|
}
|
|
|
|
/**
|
|
* 분할 패널 설정
|
|
*/
|
|
export interface ScreenSplitPanel {
|
|
id: number;
|
|
screenId: number;
|
|
leftEmbeddingId: number;
|
|
rightEmbeddingId: number;
|
|
dataTransferId: number;
|
|
layoutConfig: LayoutConfig;
|
|
companyCode: string;
|
|
createdAt: string;
|
|
updatedAt: string;
|
|
|
|
// 조인된 데이터
|
|
leftEmbedding?: ScreenEmbedding;
|
|
rightEmbedding?: ScreenEmbedding;
|
|
dataTransfer?: ScreenDataTransfer;
|
|
}
|
|
|
|
// ============================================
|
|
// 4. 컴포넌트 인터페이스
|
|
// ============================================
|
|
|
|
/**
|
|
* 데이터 수신 가능 컴포넌트 인터페이스
|
|
*/
|
|
export interface DataReceivable {
|
|
// 컴포넌트 ID
|
|
componentId: string;
|
|
|
|
// 컴포넌트 타입
|
|
componentType: ComponentType;
|
|
|
|
// 데이터 수신
|
|
receiveData(data: any[], mode: DataReceiveMode): Promise<void>;
|
|
|
|
// 현재 데이터 가져오기
|
|
getData(): any;
|
|
|
|
// 데이터 초기화
|
|
clearData(): void;
|
|
|
|
// 검증
|
|
validate(): boolean;
|
|
|
|
// 이벤트 리스너
|
|
onDataReceived?: (data: any[]) => void;
|
|
onDataCleared?: () => void;
|
|
}
|
|
|
|
/**
|
|
* 선택 가능 컴포넌트 인터페이스
|
|
*/
|
|
export interface Selectable {
|
|
// 선택된 행/항목 가져오기
|
|
getSelectedRows(): any[];
|
|
|
|
// 선택 초기화
|
|
clearSelection(): void;
|
|
|
|
// 전체 선택
|
|
selectAll(): void;
|
|
|
|
// 선택 이벤트
|
|
onSelectionChanged?: (selectedRows: any[]) => void;
|
|
}
|
|
|
|
/**
|
|
* 임베드된 화면 핸들
|
|
*/
|
|
export interface EmbeddedScreenHandle {
|
|
// 선택된 행 가져오기
|
|
getSelectedRows(): any[];
|
|
|
|
// 선택 초기화
|
|
clearSelection(): void;
|
|
|
|
// 데이터 수신
|
|
receiveData(data: any[], receivers: DataReceiver[]): Promise<void>;
|
|
|
|
// 현재 데이터 가져오기
|
|
getData(): any;
|
|
}
|
|
|
|
// ============================================
|
|
// 5. API 응답 타입
|
|
// ============================================
|
|
|
|
/**
|
|
* API 응답
|
|
*/
|
|
export interface ApiResponse<T> {
|
|
success: boolean;
|
|
data?: T;
|
|
message?: string;
|
|
error?: string;
|
|
}
|
|
|
|
/**
|
|
* 화면 임베딩 생성 요청
|
|
*/
|
|
export interface CreateScreenEmbeddingRequest {
|
|
parentScreenId: number;
|
|
childScreenId: number;
|
|
position: EmbeddingPosition;
|
|
mode: EmbeddingMode;
|
|
config?: EmbeddingConfig;
|
|
}
|
|
|
|
/**
|
|
* 데이터 전달 설정 생성 요청
|
|
*/
|
|
export interface CreateScreenDataTransferRequest {
|
|
sourceScreenId: number;
|
|
targetScreenId: number;
|
|
sourceComponentId?: string;
|
|
sourceComponentType?: string;
|
|
dataReceivers: DataReceiver[];
|
|
buttonConfig: TransferButtonConfig;
|
|
}
|
|
|
|
/**
|
|
* 분할 패널 생성 요청
|
|
*/
|
|
export interface CreateScreenSplitPanelRequest {
|
|
screenId: number;
|
|
leftEmbedding: CreateScreenEmbeddingRequest;
|
|
rightEmbedding: CreateScreenEmbeddingRequest;
|
|
dataTransfer: CreateScreenDataTransferRequest;
|
|
layoutConfig: LayoutConfig;
|
|
}
|
|
|
|
// ============================================
|
|
// 6. 유틸리티 타입
|
|
// ============================================
|
|
|
|
/**
|
|
* 데이터 전달 결과
|
|
*/
|
|
export interface DataTransferResult {
|
|
success: boolean;
|
|
transferredCount: number;
|
|
errors?: Array<{
|
|
componentId: string;
|
|
error: string;
|
|
}>;
|
|
}
|
|
|
|
/**
|
|
* 매핑 결과
|
|
*/
|
|
export interface MappingResult {
|
|
success: boolean;
|
|
mappedData: any[];
|
|
errors?: string[];
|
|
}
|
|
|
|
/**
|
|
* 검증 결과
|
|
*/
|
|
export interface ValidationResult {
|
|
valid: boolean;
|
|
errors?: string[];
|
|
}
|
|
|