fix: 분할패널 연결 필터에 operator equals 누락으로 인한 조회 실패 수정 : 우측 패널에 연관 데이터(부서인원)가 조회되지 않던 문제 수정
- 재고이력에서 품번으로 출력안되는 문제 해결 : 엔티티 조인 쿼리 생성 시 동일한 컬럼 별칭이 중복 생성되어 SQL 에러 발생하던 문제 방지
This commit is contained in:
parent
585febfb52
commit
c31b0540aa
|
|
@ -334,6 +334,10 @@ export class EntityJoinService {
|
||||||
);
|
);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
// 🔧 _label 별칭 중복 방지를 위한 Set
|
||||||
|
// 같은 sourceColumn에서 여러 조인 설정이 있을 때 _label은 첫 번째만 생성
|
||||||
|
const generatedLabelAliases = new Set<string>();
|
||||||
|
|
||||||
const joinColumns = joinConfigs
|
const joinColumns = joinConfigs
|
||||||
.map((config) => {
|
.map((config) => {
|
||||||
const aliasKey = `${config.referenceTable}:${config.sourceColumn}`;
|
const aliasKey = `${config.referenceTable}:${config.sourceColumn}`;
|
||||||
|
|
@ -368,16 +372,26 @@ export class EntityJoinService {
|
||||||
|
|
||||||
// _label 필드도 함께 SELECT (프론트엔드 getColumnUniqueValues용)
|
// _label 필드도 함께 SELECT (프론트엔드 getColumnUniqueValues용)
|
||||||
// sourceColumn_label 형식으로 추가
|
// sourceColumn_label 형식으로 추가
|
||||||
resultColumns.push(
|
// 🔧 중복 방지: 같은 sourceColumn에서 _label은 첫 번째만 생성
|
||||||
`COALESCE(${alias}.${col}::TEXT, '') AS ${config.sourceColumn}_label`
|
const labelAlias = `${config.sourceColumn}_label`;
|
||||||
);
|
if (!generatedLabelAliases.has(labelAlias)) {
|
||||||
|
resultColumns.push(
|
||||||
|
`COALESCE(${alias}.${col}::TEXT, '') AS ${labelAlias}`
|
||||||
|
);
|
||||||
|
generatedLabelAliases.add(labelAlias);
|
||||||
|
}
|
||||||
|
|
||||||
// 🆕 referenceColumn (PK)도 항상 SELECT (parentDataMapping용)
|
// 🆕 referenceColumn (PK)도 항상 SELECT (parentDataMapping용)
|
||||||
// 예: customer_code, item_number 등
|
// 예: customer_code, item_number 등
|
||||||
// col과 동일해도 별도의 alias로 추가 (customer_code as customer_code)
|
// col과 동일해도 별도의 alias로 추가 (customer_code as customer_code)
|
||||||
resultColumns.push(
|
// 🔧 중복 방지: referenceColumn도 한 번만 추가
|
||||||
`COALESCE(${alias}.${config.referenceColumn}::TEXT, '') AS ${config.referenceColumn}`
|
const refColAlias = config.referenceColumn;
|
||||||
);
|
if (!generatedLabelAliases.has(refColAlias)) {
|
||||||
|
resultColumns.push(
|
||||||
|
`COALESCE(${alias}.${config.referenceColumn}::TEXT, '') AS ${refColAlias}`
|
||||||
|
);
|
||||||
|
generatedLabelAliases.add(refColAlias);
|
||||||
|
}
|
||||||
} else {
|
} else {
|
||||||
resultColumns.push(
|
resultColumns.push(
|
||||||
`COALESCE(main.${col}::TEXT, '') AS ${config.aliasColumn}`
|
`COALESCE(main.${col}::TEXT, '') AS ${config.aliasColumn}`
|
||||||
|
|
@ -392,6 +406,11 @@ export class EntityJoinService {
|
||||||
|
|
||||||
const individualAlias = `${config.sourceColumn}_${col}`;
|
const individualAlias = `${config.sourceColumn}_${col}`;
|
||||||
|
|
||||||
|
// 🔧 중복 방지: 같은 alias가 이미 생성되었으면 스킵
|
||||||
|
if (generatedLabelAliases.has(individualAlias)) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
if (isJoinTableColumn) {
|
if (isJoinTableColumn) {
|
||||||
// 조인 테이블 컬럼은 조인 별칭 사용
|
// 조인 테이블 컬럼은 조인 별칭 사용
|
||||||
resultColumns.push(
|
resultColumns.push(
|
||||||
|
|
@ -403,6 +422,7 @@ export class EntityJoinService {
|
||||||
`COALESCE(main.${col}::TEXT, '') AS ${individualAlias}`
|
`COALESCE(main.${col}::TEXT, '') AS ${individualAlias}`
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
generatedLabelAliases.add(individualAlias);
|
||||||
});
|
});
|
||||||
|
|
||||||
// 🆕 referenceColumn (PK)도 함께 SELECT (parentDataMapping용)
|
// 🆕 referenceColumn (PK)도 함께 SELECT (parentDataMapping용)
|
||||||
|
|
@ -410,11 +430,13 @@ export class EntityJoinService {
|
||||||
config.referenceTable && config.referenceTable !== tableName;
|
config.referenceTable && config.referenceTable !== tableName;
|
||||||
if (
|
if (
|
||||||
isJoinTableColumn &&
|
isJoinTableColumn &&
|
||||||
!displayColumns.includes(config.referenceColumn)
|
!displayColumns.includes(config.referenceColumn) &&
|
||||||
|
!generatedLabelAliases.has(config.referenceColumn) // 🔧 중복 방지
|
||||||
) {
|
) {
|
||||||
resultColumns.push(
|
resultColumns.push(
|
||||||
`COALESCE(${alias}.${config.referenceColumn}::TEXT, '') AS ${config.referenceColumn}`
|
`COALESCE(${alias}.${config.referenceColumn}::TEXT, '') AS ${config.referenceColumn}`
|
||||||
);
|
);
|
||||||
|
generatedLabelAliases.add(config.referenceColumn);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -924,10 +924,15 @@ export const SplitPanelLayoutComponent: React.FC<SplitPanelLayoutComponentProps>
|
||||||
const { entityJoinApi } = await import("@/lib/api/entityJoin");
|
const { entityJoinApi } = await import("@/lib/api/entityJoin");
|
||||||
|
|
||||||
// 복합키 조건 생성
|
// 복합키 조건 생성
|
||||||
|
// 🔧 entity 타입 컬럼은 코드 값으로 정확히 매칭해야 하므로 operator: 'equals' 사용
|
||||||
const searchConditions: Record<string, any> = {};
|
const searchConditions: Record<string, any> = {};
|
||||||
keys.forEach((key) => {
|
keys.forEach((key) => {
|
||||||
if (key.leftColumn && key.rightColumn && leftItem[key.leftColumn] !== undefined) {
|
if (key.leftColumn && key.rightColumn && leftItem[key.leftColumn] !== undefined) {
|
||||||
searchConditions[key.rightColumn] = leftItem[key.leftColumn];
|
// 연결 필터는 정확한 값 매칭이 필요하므로 equals 연산자 사용
|
||||||
|
searchConditions[key.rightColumn] = {
|
||||||
|
value: leftItem[key.leftColumn],
|
||||||
|
operator: "equals",
|
||||||
|
};
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
@ -1033,16 +1038,24 @@ export const SplitPanelLayoutComponent: React.FC<SplitPanelLayoutComponentProps>
|
||||||
|
|
||||||
if (keys && keys.length > 0) {
|
if (keys && keys.length > 0) {
|
||||||
// 복합키
|
// 복합키
|
||||||
|
// 🔧 entity 타입 컬럼은 코드 값으로 정확히 매칭해야 하므로 operator: 'equals' 사용
|
||||||
keys.forEach((key) => {
|
keys.forEach((key) => {
|
||||||
if (key.leftColumn && key.rightColumn && leftItem[key.leftColumn] !== undefined) {
|
if (key.leftColumn && key.rightColumn && leftItem[key.leftColumn] !== undefined) {
|
||||||
searchConditions[key.rightColumn] = leftItem[key.leftColumn];
|
searchConditions[key.rightColumn] = {
|
||||||
|
value: leftItem[key.leftColumn],
|
||||||
|
operator: "equals",
|
||||||
|
};
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
} else {
|
} else {
|
||||||
// 단일키
|
// 단일키
|
||||||
|
// 🔧 entity 타입 컬럼은 코드 값으로 정확히 매칭해야 하므로 operator: 'equals' 사용
|
||||||
const leftValue = leftItem[leftColumn];
|
const leftValue = leftItem[leftColumn];
|
||||||
if (leftValue !== undefined) {
|
if (leftValue !== undefined) {
|
||||||
searchConditions[rightColumn] = leftValue;
|
searchConditions[rightColumn] = {
|
||||||
|
value: leftValue,
|
||||||
|
operator: "equals",
|
||||||
|
};
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue