feat: Enhance category column handling and data mapping
- Updated the `getCategoryColumnsByCompany` and `getCategoryColumnsByMenu` functions to exclude reference columns from category column queries, improving data integrity. - Modified the `TableManagementService` to include `category_ref` in the column management logic, ensuring proper handling of category references during data operations. - Enhanced the frontend components to support category reference mapping, allowing for better data representation and user interaction. - Implemented category label conversion in various components to improve the display of category data, ensuring a seamless user experience.
This commit is contained in:
@@ -1769,6 +1769,7 @@ export async function getCategoryColumnsByCompany(
|
||||
let columnsResult;
|
||||
|
||||
// 최고 관리자인 경우 company_code = '*'인 카테고리 컬럼 조회
|
||||
// category_ref가 설정된 컬럼은 제외 (참조 컬럼은 자체 값 관리 안 함)
|
||||
if (companyCode === "*") {
|
||||
const columnsQuery = `
|
||||
SELECT DISTINCT
|
||||
@@ -1788,15 +1789,15 @@ export async function getCategoryColumnsByCompany(
|
||||
ON ttc.table_name = tl.table_name
|
||||
WHERE ttc.input_type = 'category'
|
||||
AND ttc.company_code = '*'
|
||||
AND (ttc.category_ref IS NULL OR ttc.category_ref = '')
|
||||
ORDER BY ttc.table_name, ttc.column_name
|
||||
`;
|
||||
|
||||
columnsResult = await pool.query(columnsQuery);
|
||||
logger.info("✅ 최고 관리자: 전체 카테고리 컬럼 조회 완료", {
|
||||
logger.info("최고 관리자: 전체 카테고리 컬럼 조회 완료 (참조 제외)", {
|
||||
rowCount: columnsResult.rows.length
|
||||
});
|
||||
} else {
|
||||
// 일반 회사: 해당 회사의 카테고리 컬럼만 조회
|
||||
const columnsQuery = `
|
||||
SELECT DISTINCT
|
||||
ttc.table_name AS "tableName",
|
||||
@@ -1815,11 +1816,12 @@ export async function getCategoryColumnsByCompany(
|
||||
ON ttc.table_name = tl.table_name
|
||||
WHERE ttc.input_type = 'category'
|
||||
AND ttc.company_code = $1
|
||||
AND (ttc.category_ref IS NULL OR ttc.category_ref = '')
|
||||
ORDER BY ttc.table_name, ttc.column_name
|
||||
`;
|
||||
|
||||
columnsResult = await pool.query(columnsQuery, [companyCode]);
|
||||
logger.info("✅ 회사별 카테고리 컬럼 조회 완료", {
|
||||
logger.info("회사별 카테고리 컬럼 조회 완료 (참조 제외)", {
|
||||
companyCode,
|
||||
rowCount: columnsResult.rows.length
|
||||
});
|
||||
@@ -1880,13 +1882,10 @@ export async function getCategoryColumnsByMenu(
|
||||
const { getPool } = await import("../database/db");
|
||||
const pool = getPool();
|
||||
|
||||
// 🆕 table_type_columns에서 직접 input_type = 'category'인 컬럼들을 조회
|
||||
// category_column_mapping 대신 table_type_columns 기준으로 조회
|
||||
logger.info("🔍 table_type_columns 기반 카테고리 컬럼 조회", { menuObjid, companyCode });
|
||||
|
||||
// table_type_columns에서 input_type = 'category' 컬럼 조회
|
||||
// category_ref가 설정된 컬럼은 제외 (참조 컬럼은 자체 값 관리 안 함)
|
||||
let columnsResult;
|
||||
|
||||
// 최고 관리자인 경우 모든 회사의 카테고리 컬럼 조회
|
||||
if (companyCode === "*") {
|
||||
const columnsQuery = `
|
||||
SELECT DISTINCT
|
||||
@@ -1906,15 +1905,15 @@ export async function getCategoryColumnsByMenu(
|
||||
ON ttc.table_name = tl.table_name
|
||||
WHERE ttc.input_type = 'category'
|
||||
AND ttc.company_code = '*'
|
||||
AND (ttc.category_ref IS NULL OR ttc.category_ref = '')
|
||||
ORDER BY ttc.table_name, ttc.column_name
|
||||
`;
|
||||
|
||||
columnsResult = await pool.query(columnsQuery);
|
||||
logger.info("✅ 최고 관리자: 전체 카테고리 컬럼 조회 완료", {
|
||||
logger.info("최고 관리자: 메뉴별 카테고리 컬럼 조회 완료 (참조 제외)", {
|
||||
rowCount: columnsResult.rows.length
|
||||
});
|
||||
} else {
|
||||
// 일반 회사: 해당 회사의 카테고리 컬럼만 조회
|
||||
const columnsQuery = `
|
||||
SELECT DISTINCT
|
||||
ttc.table_name AS "tableName",
|
||||
@@ -1933,11 +1932,12 @@ export async function getCategoryColumnsByMenu(
|
||||
ON ttc.table_name = tl.table_name
|
||||
WHERE ttc.input_type = 'category'
|
||||
AND ttc.company_code = $1
|
||||
AND (ttc.category_ref IS NULL OR ttc.category_ref = '')
|
||||
ORDER BY ttc.table_name, ttc.column_name
|
||||
`;
|
||||
|
||||
columnsResult = await pool.query(columnsQuery, [companyCode]);
|
||||
logger.info("✅ 회사별 카테고리 컬럼 조회 완료", {
|
||||
logger.info("회사별 메뉴 카테고리 컬럼 조회 완료 (참조 제외)", {
|
||||
companyCode,
|
||||
rowCount: columnsResult.rows.length
|
||||
});
|
||||
|
||||
@@ -518,8 +518,8 @@ export class TableManagementService {
|
||||
table_name, column_name, column_label, input_type, detail_settings,
|
||||
code_category, code_value, reference_table, reference_column,
|
||||
display_column, display_order, is_visible, is_nullable,
|
||||
company_code, created_date, updated_date
|
||||
) VALUES ($1, $2, $3, $4, $5, $6, $7, $8, $9, $10, $11, $12, 'Y', $13, NOW(), NOW())
|
||||
company_code, category_ref, created_date, updated_date
|
||||
) VALUES ($1, $2, $3, $4, $5, $6, $7, $8, $9, $10, $11, $12, 'Y', $13, $14, NOW(), NOW())
|
||||
ON CONFLICT (table_name, column_name, company_code)
|
||||
DO UPDATE SET
|
||||
column_label = COALESCE(EXCLUDED.column_label, table_type_columns.column_label),
|
||||
@@ -532,6 +532,7 @@ export class TableManagementService {
|
||||
display_column = COALESCE(EXCLUDED.display_column, table_type_columns.display_column),
|
||||
display_order = COALESCE(EXCLUDED.display_order, table_type_columns.display_order),
|
||||
is_visible = COALESCE(EXCLUDED.is_visible, table_type_columns.is_visible),
|
||||
category_ref = EXCLUDED.category_ref,
|
||||
updated_date = NOW()`,
|
||||
[
|
||||
tableName,
|
||||
@@ -547,6 +548,7 @@ export class TableManagementService {
|
||||
settings.displayOrder || 0,
|
||||
settings.isVisible !== undefined ? settings.isVisible : true,
|
||||
companyCode,
|
||||
settings.categoryRef || null,
|
||||
]
|
||||
);
|
||||
|
||||
@@ -4553,7 +4555,8 @@ export class TableManagementService {
|
||||
END as "detailSettings",
|
||||
ttc.is_nullable as "isNullable",
|
||||
ic.data_type as "dataType",
|
||||
ttc.company_code as "companyCode"
|
||||
ttc.company_code as "companyCode",
|
||||
ttc.category_ref as "categoryRef"
|
||||
FROM table_type_columns ttc
|
||||
LEFT JOIN information_schema.columns ic
|
||||
ON ttc.table_name = ic.table_name AND ttc.column_name = ic.column_name
|
||||
@@ -4630,20 +4633,24 @@ export class TableManagementService {
|
||||
}
|
||||
|
||||
const inputTypes: ColumnTypeInfo[] = rawInputTypes.map((col) => {
|
||||
const baseInfo = {
|
||||
const baseInfo: any = {
|
||||
tableName: tableName,
|
||||
columnName: col.columnName,
|
||||
displayName: col.displayName,
|
||||
dataType: col.dataType || "varchar",
|
||||
inputType: col.inputType,
|
||||
detailSettings: col.detailSettings,
|
||||
description: "", // 필수 필드 추가
|
||||
isNullable: col.isNullable === "Y" ? "Y" : "N", // 🔥 FIX: string 타입으로 변환
|
||||
description: "",
|
||||
isNullable: col.isNullable === "Y" ? "Y" : "N",
|
||||
isPrimaryKey: false,
|
||||
displayOrder: 0,
|
||||
isVisible: true,
|
||||
};
|
||||
|
||||
if (col.categoryRef) {
|
||||
baseInfo.categoryRef = col.categoryRef;
|
||||
}
|
||||
|
||||
// 카테고리 타입인 경우 categoryMenus 추가
|
||||
if (
|
||||
col.inputType === "category" &&
|
||||
|
||||
Reference in New Issue
Block a user