Files
invyone/backend-spring/src/main/resources/mapper/screenManagement.xml
T

1314 lines
38 KiB
XML

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
"http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="screenManagement">
<!-- ─── Screen definitions ──────────────────────────────────────── -->
<select id="checkScreenCodeExists" parameterType="map" resultType="int">
SELECT COUNT(*)
FROM SCREEN_DEFINITIONS
WHERE SCREEN_CODE = #{screenCode}
AND IS_ACTIVE != 'D'
</select>
<insert id="insertScreen" parameterType="map" useGeneratedKeys="false">
INSERT INTO SCREEN_DEFINITIONS (
SCREEN_NAME
, SCREEN_CODE
, TABLE_NAME
, COMPANY_CODE
, DESCRIPTION
, CREATED_BY
, DB_SOURCE_TYPE
, DB_CONNECTION_ID
, DATA_SOURCE_TYPE
, REST_API_CONNECTION_ID
, REST_API_ENDPOINT
, REST_API_JSON_PATH
) VALUES (
#{screenName}
, #{screenCode}
, #{tableName}
, #{companyCode}
, #{description}
, #{createdBy}
, #{dbSourceType}
, #{dbConnectionId}
, #{dataSourceType}
, #{restApiConnectionId}
, #{restApiEndpoint}
, #{restApiJsonPath}
)
RETURNING
SCREEN_ID
, SCREEN_NAME
, SCREEN_CODE
, TABLE_NAME
, COMPANY_CODE
, DESCRIPTION
, IS_ACTIVE
, CREATED_DATE
, CREATED_BY
, UPDATED_DATE
, UPDATED_BY
, DB_SOURCE_TYPE
, DB_CONNECTION_ID
, DATA_SOURCE_TYPE
, REST_API_CONNECTION_ID
, REST_API_ENDPOINT
, REST_API_JSON_PATH
</insert>
<select id="selectScreenList" parameterType="map" resultType="map">
SELECT
SD.*
FROM SCREEN_DEFINITIONS SD
WHERE SD.IS_ACTIVE != 'D'
<if test="companyCode != null and companyCode != &quot;*&quot;">
AND (SD.COMPANY_CODE = #{companyCode} OR SD.COMPANY_CODE = '*')
</if>
<if test="searchTerm != null and searchTerm != ''">
AND (SD.SCREEN_NAME ILIKE #{searchLike}
OR SD.SCREEN_CODE ILIKE #{searchLike}
OR SD.TABLE_NAME ILIKE #{searchLike})
</if>
<if test="excludePop != null and excludePop == true">
AND NOT EXISTS (
SELECT 1
FROM SCREEN_LAYOUTS_POP SLP
WHERE SLP.SCREEN_ID = SD.SCREEN_ID
)
</if>
ORDER BY SD.CREATED_DATE DESC
LIMIT #{size} OFFSET #{offset}
</select>
<select id="countScreenList" parameterType="map" resultType="int">
SELECT COUNT(*)
FROM SCREEN_DEFINITIONS SD
WHERE SD.IS_ACTIVE != 'D'
<if test="companyCode != null and companyCode != &quot;*&quot;">
AND (SD.COMPANY_CODE = #{companyCode} OR SD.COMPANY_CODE = '*')
</if>
<if test="searchTerm != null and searchTerm != ''">
AND (SD.SCREEN_NAME ILIKE #{searchLike}
OR SD.SCREEN_CODE ILIKE #{searchLike}
OR SD.TABLE_NAME ILIKE #{searchLike})
</if>
<if test="excludePop != null and excludePop == true">
AND NOT EXISTS (
SELECT 1
FROM SCREEN_LAYOUTS_POP SLP
WHERE SLP.SCREEN_ID = SD.SCREEN_ID
)
</if>
</select>
<select id="selectScreenById" parameterType="map" resultType="map">
SELECT
*
FROM SCREEN_DEFINITIONS
WHERE SCREEN_ID = #{screenId}
LIMIT 1
</select>
<update id="updateScreen" parameterType="map">
UPDATE SCREEN_DEFINITIONS
SET
SCREEN_NAME = #{screenName}
, DESCRIPTION = #{description}
, IS_ACTIVE = #{isActive}
, UPDATED_BY = #{updatedBy}
, UPDATED_DATE = NOW()
WHERE SCREEN_ID = #{screenId}
</update>
<update id="updateScreenInfo" parameterType="map">
UPDATE SCREEN_DEFINITIONS
SET
SCREEN_NAME = #{screenName}
, TABLE_NAME = #{tableName}
, DESCRIPTION = #{description}
, IS_ACTIVE = #{isActive}
, UPDATED_DATE = NOW()
, DATA_SOURCE_TYPE = #{dataSourceType}
, DB_SOURCE_TYPE = #{dbSourceType}
, DB_CONNECTION_ID = #{dbConnectionId}
, REST_API_CONNECTION_ID = #{restApiConnectionId}
, REST_API_ENDPOINT = #{restApiEndpoint}
, REST_API_JSON_PATH = #{restApiJsonPath}
WHERE SCREEN_ID = #{screenId}
</update>
<update id="updateScreenTableName" parameterType="map">
UPDATE SCREEN_DEFINITIONS
SET
TABLE_NAME = #{tableName}
, UPDATED_DATE = NOW()
WHERE SCREEN_ID = #{screenId}
</update>
<update id="softDeleteScreen" parameterType="map">
UPDATE SCREEN_DEFINITIONS
SET
IS_ACTIVE = 'D'
, DELETED_DATE = NOW()
, DELETED_BY = #{deletedBy}
, DELETE_REASON = #{deleteReason}
, UPDATED_DATE = NOW()
, UPDATED_BY = #{deletedBy}
WHERE SCREEN_ID = #{screenId}
</update>
<update id="deactivateMenuAssignmentsByScreen" parameterType="map">
UPDATE SCREEN_MENU_ASSIGNMENTS
SET
IS_ACTIVE = 'N'
WHERE SCREEN_ID = #{screenId}
AND IS_ACTIVE = 'Y'
</update>
<delete id="deleteScreenGroupLinks" parameterType="map">
DELETE FROM SCREEN_GROUP_SCREENS
WHERE SCREEN_ID = #{screenId}
</delete>
<update id="restoreScreen" parameterType="map">
UPDATE SCREEN_DEFINITIONS
SET
IS_ACTIVE = 'Y'
, DELETED_DATE = NULL
, DELETED_BY = NULL
, DELETE_REASON = NULL
, UPDATED_DATE = NOW()
, UPDATED_BY = #{restoredBy}
WHERE SCREEN_ID = #{screenId}
</update>
<update id="reactivateMenuAssignmentsByScreen" parameterType="map">
UPDATE SCREEN_MENU_ASSIGNMENTS
SET
IS_ACTIVE = 'Y'
WHERE SCREEN_ID = #{screenId}
AND IS_ACTIVE = 'N'
</update>
<delete id="permanentDeleteLayoutV1" parameterType="map">
DELETE FROM SCREEN_LAYOUTS
WHERE SCREEN_ID = #{screenId}
</delete>
<delete id="permanentDeleteMenuAssignmentsByScreen" parameterType="map">
DELETE FROM SCREEN_MENU_ASSIGNMENTS
WHERE SCREEN_ID = #{screenId}
</delete>
<delete id="permanentDeleteScreen" parameterType="map">
DELETE FROM SCREEN_DEFINITIONS
WHERE SCREEN_ID = #{screenId}
</delete>
<select id="selectDeletedScreenList" parameterType="map" resultType="map">
SELECT
*
FROM SCREEN_DEFINITIONS
WHERE IS_ACTIVE = 'D'
<if test="companyCode != null and companyCode != &quot;*&quot;">
AND (COMPANY_CODE = #{companyCode} OR COMPANY_CODE = '*')
</if>
ORDER BY DELETED_DATE DESC NULLS LAST
LIMIT #{size} OFFSET #{offset}
</select>
<select id="countDeletedScreenList" parameterType="map" resultType="int">
SELECT COUNT(*)
FROM SCREEN_DEFINITIONS
WHERE IS_ACTIVE = 'D'
<if test="companyCode != null and companyCode != &quot;*&quot;">
AND (COMPANY_CODE = #{companyCode} OR COMPANY_CODE = '*')
</if>
</select>
<select id="selectTableLabelsByNames" parameterType="map" resultType="map">
SELECT
TABLE_NAME
, TABLE_LABEL
FROM TABLE_LABELS
WHERE TABLE_NAME IN
<foreach collection="tableNames" item="name" open="(" separator="," close=")">
#{name}
</foreach>
</select>
<select id="checkDuplicateScreenName" parameterType="map" resultType="int">
SELECT COUNT(*)
FROM SCREEN_DEFINITIONS
WHERE (COMPANY_CODE = #{companyCode} OR COMPANY_CODE = '*')
AND SCREEN_NAME = #{screenName}
AND DELETED_DATE IS NULL
</select>
<select id="checkScreenCodeForRestore" parameterType="map" resultType="int">
SELECT COUNT(*)
FROM SCREEN_DEFINITIONS
WHERE SCREEN_CODE = #{screenCode}
AND IS_ACTIVE != 'D'
AND SCREEN_ID != #{screenId}
</select>
<!-- ─── Screen code generation ──────────────────────────────────── -->
<select id="pgAdvisoryXactLock" parameterType="map" resultType="map">
SELECT PG_ADVISORY_XACT_LOCK(#{lockId})
</select>
<select id="selectScreenCodesByPattern" parameterType="map" resultType="map">
SELECT
SCREEN_CODE
FROM SCREEN_DEFINITIONS
WHERE SCREEN_CODE LIKE #{pattern}
ORDER BY SCREEN_CODE DESC
</select>
<!-- ─── Layout V1 ───────────────────────────────────────────────── -->
<delete id="deleteAllLayoutV1" parameterType="map">
DELETE FROM SCREEN_LAYOUTS
WHERE SCREEN_ID = #{screenId}
</delete>
<insert id="insertLayoutV1Component" parameterType="map">
INSERT INTO SCREEN_LAYOUTS (
SCREEN_ID
, COMPONENT_TYPE
, COMPONENT_ID
, PARENT_ID
, POSITION_X
, POSITION_Y
, WIDTH
, HEIGHT
, PROPERTIES
, DISPLAY_ORDER
) VALUES (
#{screenId}
, #{componentType}
, #{componentId}
, #{parentId}
, #{positionX}
, #{positionY}
, #{width}
, #{height}
, #{properties}::jsonb
, #{displayOrder}
)
</insert>
<select id="selectLayoutV1ByScreen" parameterType="map" resultType="map">
SELECT
*
FROM SCREEN_LAYOUTS
WHERE SCREEN_ID = #{screenId}
ORDER BY DISPLAY_ORDER ASC NULLS LAST, LAYOUT_ID ASC
</select>
<!-- ─── Layout V2 ───────────────────────────────────────────────── -->
<select id="selectLayoutV2" parameterType="map" resultType="map">
SELECT
LAYOUT_DATA
, LAYER_NAME
, CONDITION_CONFIG
, COMPANY_CODE
FROM SCREEN_LAYOUTS_V2
WHERE SCREEN_ID = #{screenId}
AND (COMPANY_CODE = #{companyCode} OR COMPANY_CODE = '*')
<if test="layerId != null">AND LAYER_ID = #{layerId}</if>
ORDER BY LAYER_ID ASC
LIMIT 1
</select>
<insert id="upsertLayoutV2" parameterType="map">
INSERT INTO SCREEN_LAYOUTS_V2 (
SCREEN_ID
, COMPANY_CODE
, LAYER_ID
, LAYER_NAME
, LAYOUT_DATA
, CREATED_AT
, UPDATED_AT
) VALUES (
#{screenId}
, #{companyCode}
, #{layerId}
, #{layerName}
, #{layoutData}::jsonb
, NOW()
, NOW()
)
ON CONFLICT (SCREEN_ID, COMPANY_CODE, LAYER_ID) DO UPDATE SET
LAYOUT_DATA = EXCLUDED.LAYOUT_DATA
, LAYER_NAME = EXCLUDED.LAYER_NAME
, UPDATED_AT = NOW()
</insert>
<insert id="upsertLayoutV2WithCondition" parameterType="map">
INSERT INTO SCREEN_LAYOUTS_V2 (
SCREEN_ID
, COMPANY_CODE
, LAYER_ID
, LAYER_NAME
, CONDITION_CONFIG
, LAYOUT_DATA
, CREATED_AT
, UPDATED_AT
) VALUES (
#{screenId}
, #{companyCode}
, #{layerId}
, #{layerName}
, #{conditionConfig}::jsonb
, #{layoutData}::jsonb
, NOW()
, NOW()
)
ON CONFLICT (SCREEN_ID, COMPANY_CODE, LAYER_ID) DO UPDATE SET
LAYOUT_DATA = EXCLUDED.LAYOUT_DATA
, LAYER_NAME = EXCLUDED.LAYER_NAME
, CONDITION_CONFIG = EXCLUDED.CONDITION_CONFIG
, UPDATED_AT = NOW()
</insert>
<update id="updateScreenMainTable" parameterType="map">
UPDATE SCREEN_DEFINITIONS
SET
TABLE_NAME = #{tableName}
, UPDATED_DATE = NOW()
WHERE SCREEN_ID = #{screenId}
</update>
<!-- ─── Layer management ────────────────────────────────────────── -->
<select id="selectLayersByScreen" parameterType="map" resultType="map">
SELECT
LAYER_ID
, LAYER_NAME
, COALESCE(CONDITION_CONFIG, '{}') AS CONDITION_CONFIG
, JSONB_ARRAY_LENGTH(COALESCE(LAYOUT_DATA->'components', '[]'::jsonb)) AS COMPONENT_COUNT
, UPDATED_AT
FROM SCREEN_LAYOUTS_V2
WHERE SCREEN_ID = #{screenId}
<if test='companyCode != null and companyCode != "*"'>
AND (COMPANY_CODE = #{companyCode} OR COMPANY_CODE = '*')
</if>
ORDER BY LAYER_ID
</select>
<insert id="upsertDefaultLayer" parameterType="map">
INSERT INTO SCREEN_LAYOUTS_V2 (
SCREEN_ID
, COMPANY_CODE
, LAYER_ID
, LAYER_NAME
, LAYOUT_DATA
, CREATED_AT
, UPDATED_AT
) VALUES (
#{screenId}
, #{companyCode}
, 1
, '기본 레이어'
, #{layoutData}::jsonb
, NOW()
, NOW()
)
ON CONFLICT (SCREEN_ID, COMPANY_CODE, LAYER_ID) DO NOTHING
</insert>
<select id="selectLayerLayout" parameterType="map" resultType="map">
SELECT
LAYOUT_DATA
, LAYER_NAME
, CONDITION_CONFIG
FROM SCREEN_LAYOUTS_V2
WHERE SCREEN_ID = #{screenId}
AND (COMPANY_CODE = #{companyCode} OR COMPANY_CODE = '*')
AND LAYER_ID = #{layerId}
LIMIT 1
</select>
<delete id="deleteLayerById" parameterType="map">
DELETE FROM SCREEN_LAYOUTS_V2
WHERE SCREEN_ID = #{screenId}
AND (COMPANY_CODE = #{companyCode} OR COMPANY_CODE = '*')
AND LAYER_ID = #{layerId}
</delete>
<update id="updateLayerCondition" parameterType="map">
UPDATE SCREEN_LAYOUTS_V2
<set>
CONDITION_CONFIG = #{conditionConfig}::jsonb,
UPDATED_AT = NOW()
<if test="layerName != null">, LAYER_NAME = #{layerName}</if>
</set>
WHERE SCREEN_ID = #{screenId}
AND (COMPANY_CODE = #{companyCode} OR COMPANY_CODE = '*')
AND LAYER_ID = #{layerId}
</update>
<select id="selectMaxLayerId" parameterType="map" resultType="map">
SELECT
COALESCE(MAX(LAYER_ID), 1) AS MAX_ID
FROM SCREEN_LAYOUTS_V2
WHERE SCREEN_ID = #{screenId}
AND (COMPANY_CODE = #{companyCode} OR COMPANY_CODE = '*')
</select>
<insert id="insertLayerForZone" parameterType="map">
INSERT INTO SCREEN_LAYOUTS_V2 (
SCREEN_ID
, COMPANY_CODE
, LAYOUT_DATA
, LAYER_ID
, LAYER_NAME
, CONDITION_CONFIG
) VALUES (
#{screenId}
, #{companyCode}
, #{layoutData}::jsonb
, #{layerId}
, #{layerName}
, #{conditionConfig}::jsonb
)
ON CONFLICT (SCREEN_ID, COMPANY_CODE, LAYER_ID) DO UPDATE SET
LAYOUT_DATA = EXCLUDED.LAYOUT_DATA
, LAYER_NAME = EXCLUDED.LAYER_NAME
, CONDITION_CONFIG = EXCLUDED.CONDITION_CONFIG
, UPDATED_AT = NOW()
</insert>
<!-- ─── Zone management ─────────────────────────────────────────── -->
<select id="selectZonesByScreen" parameterType="map" resultType="map">
SELECT
*
FROM SCREEN_CONDITIONAL_ZONES
WHERE SCREEN_ID = #{screenId}
<if test="companyCode != null and companyCode != &quot;*&quot;">
AND (COMPANY_CODE = #{companyCode} OR COMPANY_CODE = '*')
</if>
ORDER BY ZONE_ID
</select>
<insert id="insertZone" parameterType="map" useGeneratedKeys="false">
INSERT INTO SCREEN_CONDITIONAL_ZONES (
SCREEN_ID
, COMPANY_CODE
, ZONE_NAME
, X
, Y
, WIDTH
, HEIGHT
, TRIGGER_COMPONENT_ID
, TRIGGER_OPERATOR
) VALUES (
#{screenId}
, #{companyCode}
, #{zoneName}
, #{x}
, #{y}
, #{width}
, #{height}
, #{triggerComponentId}
, #{triggerOperator}
)
RETURNING *
</insert>
<update id="updateZone" parameterType="map">
UPDATE SCREEN_CONDITIONAL_ZONES
<set>
UPDATED_AT = NOW()
<if test="zoneName != null">, ZONE_NAME = #{zoneName}</if>
<if test="x != null">, X = #{x}</if>
<if test="y != null">, Y = #{y}</if>
<if test="width != null">, WIDTH = #{width}</if>
<if test="height != null">, HEIGHT = #{height}</if>
<if test="triggerComponentId != null">, TRIGGER_COMPONENT_ID = #{triggerComponentId}</if>
<if test="triggerOperator != null">, TRIGGER_OPERATOR = #{triggerOperator}</if>
</set>
WHERE ZONE_ID = #{zoneId}
AND (COMPANY_CODE = #{companyCode} OR COMPANY_CODE = '*')
</update>
<delete id="deleteZoneById" parameterType="map">
DELETE FROM SCREEN_CONDITIONAL_ZONES
WHERE ZONE_ID = #{zoneId}
AND (COMPANY_CODE = #{companyCode} OR COMPANY_CODE = '*')
</delete>
<update id="clearZoneConditionConfigs" parameterType="map">
UPDATE SCREEN_LAYOUTS_V2
SET
CONDITION_CONFIG = NULL
, UPDATED_AT = NOW()
WHERE (COMPANY_CODE = #{companyCode} OR COMPANY_CODE = '*')
AND CONDITION_CONFIG->>'zone_id' = #{zoneIdStr}
</update>
<select id="selectZoneById" parameterType="map" resultType="map">
SELECT
*
FROM SCREEN_CONDITIONAL_ZONES
WHERE ZONE_ID = #{zoneId}
AND (COMPANY_CODE = #{companyCode} OR COMPANY_CODE = '*')
LIMIT 1
</select>
<!-- ─── POP Layout ───────────────────────────────────────────────── -->
<select id="selectLayoutPop" parameterType="map" resultType="map">
SELECT
LAYOUT_DATA
FROM SCREEN_LAYOUTS_POP
WHERE SCREEN_ID = #{screenId}
AND (COMPANY_CODE = #{companyCode} OR COMPANY_CODE = '*')
LIMIT 1
</select>
<insert id="upsertLayoutPop" parameterType="map">
INSERT INTO SCREEN_LAYOUTS_POP (
SCREEN_ID
, COMPANY_CODE
, LAYOUT_DATA
, CREATED_AT
, UPDATED_AT
, CREATED_BY
, UPDATED_BY
) VALUES (
#{screenId}
, #{companyCode}
, #{layoutData}::jsonb
, NOW()
, NOW()
, #{userId}
, #{userId}
)
ON CONFLICT (SCREEN_ID, COMPANY_CODE) DO UPDATE SET
LAYOUT_DATA = EXCLUDED.LAYOUT_DATA
, UPDATED_AT = NOW()
, UPDATED_BY = EXCLUDED.UPDATED_BY
</insert>
<delete id="deleteLayoutPopByScreen" parameterType="map">
DELETE FROM SCREEN_LAYOUTS_POP
WHERE SCREEN_ID = #{screenId}
AND (COMPANY_CODE = #{companyCode} OR COMPANY_CODE = '*')
</delete>
<select id="selectScreenIdsWithPopLayout" parameterType="map" resultType="map">
SELECT DISTINCT
SCREEN_ID
FROM SCREEN_LAYOUTS_POP
<if test="companyCode != null and companyCode != &quot;*&quot;">
WHERE (COMPANY_CODE = #{companyCode} OR COMPANY_CODE = '*')
</if>
</select>
<!-- ─── Menu assignment ──────────────────────────────────────────── -->
<select id="checkMenuAssignmentExists" parameterType="map" resultType="map">
SELECT
ASSIGNMENT_ID
FROM SCREEN_MENU_ASSIGNMENTS
WHERE SCREEN_ID = #{screenId}
AND MENU_OBJID = #{menuObjid}
AND (COMPANY_CODE = #{companyCode} OR COMPANY_CODE = '*')
LIMIT 1
</select>
<insert id="insertMenuAssignment" parameterType="map">
INSERT INTO SCREEN_MENU_ASSIGNMENTS (
SCREEN_ID
, MENU_OBJID
, COMPANY_CODE
, DISPLAY_ORDER
, CREATED_BY
) VALUES (
#{screenId}
, #{menuObjid}
, #{companyCode}
, #{displayOrder}
, #{createdBy}
)
</insert>
<select id="selectScreenCode" parameterType="map" resultType="map">
SELECT
SCREEN_CODE
FROM SCREEN_DEFINITIONS
WHERE SCREEN_ID = #{screenId}
LIMIT 1
</select>
<select id="selectMenuType" parameterType="map" resultType="map">
SELECT
MENU_TYPE
FROM MENU_INFO
WHERE OBJID = #{menuObjid}
LIMIT 1
</select>
<update id="updateMenuInfoAssign" parameterType="map">
UPDATE MENU_INFO
SET
MENU_URL = #{menuUrl}
, SCREEN_CODE = #{screenCode}
WHERE OBJID = #{menuObjid}
</update>
<delete id="deleteMenuAssignment" parameterType="map">
DELETE FROM SCREEN_MENU_ASSIGNMENTS
WHERE SCREEN_ID = #{screenId}
AND MENU_OBJID = #{menuObjid}
AND (COMPANY_CODE = #{companyCode} OR COMPANY_CODE = '*')
</delete>
<update id="updateMenuInfoUnassign" parameterType="map">
UPDATE MENU_INFO
SET
MENU_URL = NULL
, SCREEN_CODE = NULL
WHERE OBJID = #{menuObjid}
</update>
<select id="selectScreensByMenu" parameterType="map" resultType="map">
SELECT
SD.*
FROM SCREEN_MENU_ASSIGNMENTS SMA
INNER JOIN SCREEN_DEFINITIONS SD ON SMA.SCREEN_ID = SD.SCREEN_ID
WHERE SMA.MENU_OBJID = #{menuObjid}
AND (SMA.COMPANY_CODE = #{companyCode} OR SMA.COMPANY_CODE = '*')
AND SMA.IS_ACTIVE = 'Y'
ORDER BY CASE WHEN SMA.COMPANY_CODE = #{companyCode} THEN 0 ELSE 1 END
, SMA.DISPLAY_ORDER ASC
</select>
<select id="selectMenuByScreen" parameterType="map" resultType="map">
SELECT
SMA.MENU_OBJID
, MI.MENU_NAME_KOR
FROM SCREEN_MENU_ASSIGNMENTS SMA
LEFT JOIN MENU_INFO MI ON SMA.MENU_OBJID = MI.OBJID
WHERE SMA.SCREEN_ID = #{screenId}
AND (SMA.COMPANY_CODE = #{companyCode} OR SMA.COMPANY_CODE = '*')
AND SMA.IS_ACTIVE = 'Y'
ORDER BY SMA.CREATED_DATE ASC
LIMIT 1
</select>
<update id="cleanupDeletedMenuAssignments" parameterType="map">
UPDATE SCREEN_MENU_ASSIGNMENTS
SET
IS_ACTIVE = 'N'
WHERE SCREEN_ID IN (
SELECT SCREEN_ID
FROM SCREEN_DEFINITIONS
WHERE IS_ACTIVE = 'D'
)
AND IS_ACTIVE = 'Y'
</update>
<!-- ─── Dependencies / Linked modals ────────────────────────────── -->
<select id="selectScreensWithLayouts" parameterType="map" resultType="map">
SELECT
SD.SCREEN_ID
, SD.SCREEN_NAME
, SD.SCREEN_CODE
, SD.COMPANY_CODE
, SL.LAYOUT_ID
, SL.COMPONENT_ID
, SL.COMPONENT_TYPE
, SL.PROPERTIES
FROM SCREEN_DEFINITIONS SD
LEFT JOIN SCREEN_LAYOUTS SL ON SD.SCREEN_ID = SL.SCREEN_ID
AND SL.COMPONENT_TYPE = 'component'
WHERE SD.IS_ACTIVE != 'D'
<if test="companyCode != null and companyCode != &quot;*&quot;">
AND SD.COMPANY_CODE IN (#{companyCode}, '*')
</if>
</select>
<select id="selectMenuAssignmentDeps" parameterType="map" resultType="map">
SELECT
SMA.ASSIGNMENT_ID
, SMA.MENU_OBJID
, MI.MENU_NAME_KOR
FROM SCREEN_MENU_ASSIGNMENTS SMA
LEFT JOIN MENU_INFO MI ON SMA.MENU_OBJID = MI.OBJID
WHERE SMA.SCREEN_ID = #{screenId}
AND SMA.IS_ACTIVE = 'Y'
</select>
<select id="selectLayoutsForLinkedModal" parameterType="map" resultType="map">
SELECT
LAYOUT_ID
, PROPERTIES
FROM SCREEN_LAYOUTS
WHERE SCREEN_ID = #{screenId}
AND COMPONENT_TYPE = 'component'
AND PROPERTIES IS NOT NULL
</select>
<select id="selectScreensByIds" parameterType="map" resultType="map">
SELECT
SCREEN_ID
, SCREEN_NAME
, SCREEN_CODE
FROM SCREEN_DEFINITIONS
WHERE SCREEN_ID IN
<foreach collection="ids" item="id" open="(" separator="," close=")">
#{id}
</foreach>
AND IS_ACTIVE != 'D'
ORDER BY SCREEN_NAME
</select>
<!-- ─── Copy screen ──────────────────────────────────────────────── -->
<select id="selectScreenForCopy" parameterType="map" resultType="map">
SELECT
*
FROM SCREEN_DEFINITIONS
WHERE SCREEN_ID = #{screenId}
LIMIT 1
</select>
<insert id="insertScreenCopy" parameterType="map" useGeneratedKeys="false">
INSERT INTO SCREEN_DEFINITIONS (
SCREEN_NAME
, SCREEN_CODE
, TABLE_NAME
, COMPANY_CODE
, DESCRIPTION
, CREATED_BY
, DB_SOURCE_TYPE
, DB_CONNECTION_ID
, DATA_SOURCE_TYPE
, REST_API_CONNECTION_ID
, REST_API_ENDPOINT
, REST_API_JSON_PATH
) VALUES (
#{screenName}
, #{screenCode}
, #{tableName}
, #{companyCode}
, #{description}
, #{createdBy}
, #{dbSourceType}
, #{dbConnectionId}
, #{dataSourceType}
, #{restApiConnectionId}
, #{restApiEndpoint}
, #{restApiJsonPath}
)
RETURNING
SCREEN_ID
, SCREEN_NAME
, SCREEN_CODE
, TABLE_NAME
, COMPANY_CODE
, DESCRIPTION
, IS_ACTIVE
, CREATED_DATE
, CREATED_BY
, DB_SOURCE_TYPE
, DB_CONNECTION_ID
, DATA_SOURCE_TYPE
, REST_API_CONNECTION_ID
, REST_API_ENDPOINT
, REST_API_JSON_PATH
</insert>
<select id="selectLayoutV1ForCopy" parameterType="map" resultType="map">
SELECT
*
FROM SCREEN_LAYOUTS
WHERE SCREEN_ID = #{screenId}
ORDER BY DISPLAY_ORDER ASC NULLS LAST, LAYOUT_ID ASC
</select>
<insert id="insertLayoutV1Copy" parameterType="map">
INSERT INTO SCREEN_LAYOUTS (
SCREEN_ID
, COMPONENT_TYPE
, COMPONENT_ID
, PARENT_ID
, POSITION_X
, POSITION_Y
, WIDTH
, HEIGHT
, PROPERTIES
, DISPLAY_ORDER
) VALUES (
#{screenId}
, #{componentType}
, #{componentId}
, #{parentId}
, #{positionX}
, #{positionY}
, #{width}
, #{height}
, #{properties}::jsonb
, #{displayOrder}
)
</insert>
<select id="selectLayoutV2ForCopy" parameterType="map" resultType="map">
SELECT
SCREEN_ID
, COMPANY_CODE
, LAYER_ID
, LAYER_NAME
, CONDITION_CONFIG
, LAYOUT_DATA
FROM SCREEN_LAYOUTS_V2
WHERE SCREEN_ID = #{screenId}
</select>
<insert id="insertLayoutV2Copy" parameterType="map">
INSERT INTO SCREEN_LAYOUTS_V2 (
SCREEN_ID
, COMPANY_CODE
, LAYER_ID
, LAYER_NAME
, CONDITION_CONFIG
, LAYOUT_DATA
, CREATED_AT
, UPDATED_AT
) VALUES (
#{screenId}
, #{companyCode}
, #{layerId}
, #{layerName}
, #{conditionConfig}::jsonb
, #{layoutData}::jsonb
, NOW()
, NOW()
)
ON CONFLICT (SCREEN_ID, COMPANY_CODE, LAYER_ID) DO UPDATE SET
LAYOUT_DATA = EXCLUDED.LAYOUT_DATA
, UPDATED_AT = NOW()
</insert>
<!-- ─── Layout properties update (tab references) ────────────────── -->
<select id="selectLayoutsV1ForScreen" parameterType="map" resultType="map">
SELECT
LAYOUT_ID
, PROPERTIES
FROM SCREEN_LAYOUTS
WHERE SCREEN_ID = #{screenId}
AND COMPONENT_TYPE = 'component'
AND PROPERTIES IS NOT NULL
</select>
<update id="updateLayoutV1Properties" parameterType="map">
UPDATE SCREEN_LAYOUTS
SET
PROPERTIES = #{properties}::jsonb
WHERE LAYOUT_ID = #{layoutId}
</update>
<select id="selectLayoutsV2ForScreen" parameterType="map" resultType="map">
SELECT
SCREEN_ID
, LAYER_ID
, COMPANY_CODE
, LAYOUT_DATA
FROM SCREEN_LAYOUTS_V2
WHERE SCREEN_ID = #{screenId}
AND LAYOUT_DATA IS NOT NULL
</select>
<update id="updateLayoutV2Data" parameterType="map">
UPDATE SCREEN_LAYOUTS_V2
SET
LAYOUT_DATA = #{layoutData}::jsonb
, UPDATED_AT = NOW()
WHERE SCREEN_ID = #{screenId}
AND LAYER_ID = #{layerId}
AND (COMPANY_CODE = #{companyCode} OR COMPANY_CODE = '*')
</update>
<!-- ─── Flow cleanup on screen delete ───────────────────────────── -->
<select id="selectLayoutsV2ForFlowCleanup" parameterType="map" resultType="map">
SELECT
LAYOUT_DATA
FROM SCREEN_LAYOUTS_V2
WHERE SCREEN_ID = #{screenId}
AND (COMPANY_CODE = #{companyCode} OR COMPANY_CODE = '*')
ORDER BY CASE WHEN COMPANY_CODE = #{companyCode} THEN 0 ELSE 1 END
LIMIT 1
</select>
<select id="countFlowUsageInOtherScreens" parameterType="map" resultType="int">
SELECT COUNT(*)
FROM SCREEN_LAYOUTS_V2 SLV
JOIN SCREEN_DEFINITIONS SD ON SLV.SCREEN_ID = SD.SCREEN_ID
WHERE SLV.SCREEN_ID != #{screenId}
AND SD.IS_ACTIVE != 'D'
<if test="companyCode != null and companyCode != &quot;*&quot;">
AND (SD.COMPANY_CODE = #{companyCode} OR SD.COMPANY_CODE = '*')
</if>
AND (
SLV.LAYOUT_DATA::text LIKE '%"flowId":' || #{flowId} || '%'
OR SLV.LAYOUT_DATA::text LIKE '%"flowId":"' || #{flowId} || '"%'
)
</select>
<delete id="deleteFlowStepConnections" parameterType="map">
DELETE FROM FLOW_STEP_CONNECTION
WHERE FLOW_DEFINITION_ID = #{flowId}
</delete>
<delete id="deleteFlowSteps" parameterType="map">
DELETE FROM FLOW_STEP
WHERE FLOW_DEFINITION_ID = #{flowId}
</delete>
<delete id="deleteFlowDefinition" parameterType="map">
DELETE FROM FLOW_DEFINITION
WHERE ID = #{flowId}
<if test="companyCode != null and companyCode != &quot;*&quot;">
AND (COMPANY_CODE = #{companyCode} OR COMPANY_CODE = '*')
</if>
</delete>
<delete id="deleteNodeFlowsByFlowId" parameterType="map">
DELETE FROM NODE_FLOWS
WHERE FLOW_ID = #{flowId}
<if test="companyCode != null and companyCode != &quot;*&quot;">
AND (COMPANY_CODE = #{companyCode} OR COMPANY_CODE = '*')
</if>
</delete>
<!-- ─── Copy operations ─────────────────────────────────────────── -->
<select id="selectMenuAssignmentsForCopy" parameterType="map" resultType="map">
SELECT
*
FROM SCREEN_MENU_ASSIGNMENTS
WHERE SCREEN_ID IN
<foreach collection="screenIds" item="id" open="(" separator="," close=")">
#{id}
</foreach>
AND (COMPANY_CODE = #{sourceCompanyCode} OR COMPANY_CODE = '*')
AND IS_ACTIVE = 'Y'
</select>
<insert id="insertMenuAssignmentCopy" parameterType="map">
INSERT INTO SCREEN_MENU_ASSIGNMENTS (
SCREEN_ID
, MENU_OBJID
, COMPANY_CODE
, DISPLAY_ORDER
, CREATED_BY
) VALUES (
#{screenId}
, #{menuObjid}
, #{companyCode}
, #{displayOrder}
, #{createdBy}
)
ON CONFLICT DO NOTHING
</insert>
<select id="selectCodeCategoryForCopy" parameterType="map" resultType="map">
SELECT
*
FROM CODE_CATEGORY
WHERE (COMPANY_CODE = #{sourceCompanyCode} OR COMPANY_CODE = '*')
</select>
<insert id="upsertCodeCategory" parameterType="map">
INSERT INTO CODE_CATEGORY (
CATEGORY_CODE
, CATEGORY_NAME
, COMPANY_CODE
, DESCRIPTION
) VALUES (
#{categoryCode}
, #{categoryName}
, #{targetCompanyCode}
, #{description}
)
ON CONFLICT (CATEGORY_CODE, COMPANY_CODE) DO UPDATE SET
CATEGORY_NAME = EXCLUDED.CATEGORY_NAME
, DESCRIPTION = EXCLUDED.DESCRIPTION
</insert>
<select id="selectCodeInfoForCopy" parameterType="map" resultType="map">
SELECT
*
FROM CODE_INFO
WHERE (COMPANY_CODE = #{sourceCompanyCode} OR COMPANY_CODE = '*')
AND CODE_CATEGORY = #{codeCategory}
</select>
<insert id="upsertCodeInfo" parameterType="map">
INSERT INTO CODE_INFO (
CODE_CATEGORY
, CODE_VALUE
, CODE_NAME
, COMPANY_CODE
, SORT_ORDER
, IS_ACTIVE
) VALUES (
#{codeCategory}
, #{codeValue}
, #{codeName}
, #{targetCompanyCode}
, #{sortOrder}
, #{isActive}
)
ON CONFLICT (CODE_CATEGORY, CODE_VALUE, COMPANY_CODE) DO UPDATE SET
CODE_NAME = EXCLUDED.CODE_NAME
, SORT_ORDER = EXCLUDED.SORT_ORDER
, IS_ACTIVE = EXCLUDED.IS_ACTIVE
</insert>
<select id="selectCategoryTreeForCopy" parameterType="map" resultType="map">
SELECT
*
FROM CATEGORY_TREE
WHERE (COMPANY_CODE = #{sourceCompanyCode} OR COMPANY_CODE = '*')
</select>
<insert id="upsertCategoryTree" parameterType="map">
INSERT INTO CATEGORY_TREE (
CATEGORY_CODE
, CATEGORY_NAME
, PARENT_CODE
, COMPANY_CODE
, SORT_ORDER
) VALUES (
#{categoryCode}
, #{categoryName}
, #{parentCode}
, #{targetCompanyCode}
, #{sortOrder}
)
ON CONFLICT (CATEGORY_CODE, COMPANY_CODE) DO UPDATE SET
CATEGORY_NAME = EXCLUDED.CATEGORY_NAME
, PARENT_CODE = EXCLUDED.PARENT_CODE
, SORT_ORDER = EXCLUDED.SORT_ORDER
</insert>
<select id="selectCategoryValueForCopy" parameterType="map" resultType="map">
SELECT
*
FROM CATEGORY_VALUE
WHERE (COMPANY_CODE = #{sourceCompanyCode} OR COMPANY_CODE = '*')
</select>
<insert id="upsertCategoryValue" parameterType="map">
INSERT INTO CATEGORY_VALUE (
CATEGORY_CODE
, VALUE_CODE
, VALUE_NAME
, COMPANY_CODE
, SORT_ORDER
) VALUES (
#{categoryCode}
, #{valueCode}
, #{valueName}
, #{targetCompanyCode}
, #{sortOrder}
)
ON CONFLICT (CATEGORY_CODE, VALUE_CODE, COMPANY_CODE) DO UPDATE SET
VALUE_NAME = EXCLUDED.VALUE_NAME
, SORT_ORDER = EXCLUDED.SORT_ORDER
</insert>
<select id="selectTableTypeColumnsForCopy" parameterType="map" resultType="map">
SELECT
*
FROM TABLE_TYPE_COLUMNS
WHERE (COMPANY_CODE = #{sourceCompanyCode} OR COMPANY_CODE = '*')
</select>
<insert id="upsertTableTypeColumn" parameterType="map">
INSERT INTO TABLE_TYPE_COLUMNS (
TABLE_NAME
, COLUMN_NAME
, COLUMN_LABEL
, INPUT_TYPE
, COMPANY_CODE
, IS_VISIBLE
, DISPLAY_ORDER
, IS_NULLABLE
) VALUES (
#{tableName}
, #{columnName}
, #{columnLabel}
, #{inputType}
, #{targetCompanyCode}
, #{isVisible}
, #{displayOrder}
, #{isNullable}
)
ON CONFLICT (TABLE_NAME, COLUMN_NAME, COMPANY_CODE) DO UPDATE SET
COLUMN_LABEL = EXCLUDED.COLUMN_LABEL
, INPUT_TYPE = EXCLUDED.INPUT_TYPE
, IS_VISIBLE = EXCLUDED.IS_VISIBLE
, DISPLAY_ORDER = EXCLUDED.DISPLAY_ORDER
</insert>
<select id="selectCascadingRelationForCopy" parameterType="map" resultType="map">
SELECT
*
FROM CASCADING_RELATION
WHERE (COMPANY_CODE = #{sourceCompanyCode} OR COMPANY_CODE = '*')
</select>
<insert id="upsertCascadingRelation" parameterType="map">
INSERT INTO CASCADING_RELATION (
PARENT_TABLE
, PARENT_COLUMN
, CHILD_TABLE
, CHILD_COLUMN
, COMPANY_CODE
) VALUES (
#{parentTable}
, #{parentColumn}
, #{childTable}
, #{childColumn}
, #{targetCompanyCode}
)
ON CONFLICT (PARENT_TABLE, PARENT_COLUMN, CHILD_TABLE, CHILD_COLUMN, COMPANY_CODE)
DO NOTHING
</insert>
<!-- ─── POP deploy ──────────────────────────────────────────────── -->
<select id="selectScreenByCode" parameterType="map" resultType="map">
SELECT
*
FROM SCREEN_DEFINITIONS
WHERE SCREEN_CODE = #{screenCode}
AND (COMPANY_CODE = #{companyCode} OR COMPANY_CODE = '*')
AND IS_ACTIVE != 'D'
LIMIT 1
</select>
<insert id="insertScreenForDeploy" parameterType="map" useGeneratedKeys="false">
INSERT INTO SCREEN_DEFINITIONS (
SCREEN_NAME
, SCREEN_CODE
, TABLE_NAME
, COMPANY_CODE
, DESCRIPTION
, CREATED_BY
, DB_SOURCE_TYPE
, DATA_SOURCE_TYPE
) VALUES (
#{screenName}
, #{screenCode}
, #{tableName}
, #{companyCode}
, #{description}
, #{createdBy}
, #{dbSourceType}
, #{dataSourceType}
)
RETURNING
SCREEN_ID
, SCREEN_NAME
, SCREEN_CODE
, COMPANY_CODE
</insert>
<insert id="upsertPopLayoutDeploy" parameterType="map">
INSERT INTO SCREEN_LAYOUTS_POP (
SCREEN_ID
, COMPANY_CODE
, LAYOUT_DATA
, CREATED_AT
, UPDATED_AT
, CREATED_BY
, UPDATED_BY
) VALUES (
#{screenId}
, #{companyCode}
, #{layoutData}::jsonb
, NOW()
, NOW()
, #{userId}
, #{userId}
)
ON CONFLICT (SCREEN_ID, COMPANY_CODE) DO UPDATE SET
LAYOUT_DATA = EXCLUDED.LAYOUT_DATA
, UPDATED_AT = NOW()
, UPDATED_BY = EXCLUDED.UPDATED_BY
</insert>
<!-- ─── Tables ──────────────────────────────────────────────────── -->
<select id="selectPublicTables" parameterType="map" resultType="map">
SELECT
TABLE_NAME
FROM INFORMATION_SCHEMA.TABLES
WHERE TABLE_SCHEMA = 'public'
AND TABLE_TYPE = 'BASE TABLE'
ORDER BY TABLE_NAME
</select>
<select id="selectTableInfoByName" parameterType="map" resultType="map">
SELECT
TABLE_NAME
, (SELECT COUNT(*) FROM INFORMATION_SCHEMA.COLUMNS C WHERE C.TABLE_NAME = T.TABLE_NAME) AS COLUMN_COUNT
FROM INFORMATION_SCHEMA.TABLES T
WHERE TABLE_SCHEMA = 'public'
AND TABLE_TYPE = 'BASE TABLE'
AND TABLE_NAME = #{tableName}
LIMIT 1
</select>
<select id="selectTableColumnsInfo" parameterType="map" resultType="map">
SELECT
C.COLUMN_NAME
, C.DATA_TYPE
, C.IS_NULLABLE
, C.COLUMN_DEFAULT
, C.CHARACTER_MAXIMUM_LENGTH
, C.NUMERIC_PRECISION
, C.NUMERIC_SCALE
FROM INFORMATION_SCHEMA.COLUMNS C
WHERE C.TABLE_SCHEMA = 'public'
AND C.TABLE_NAME = #{tableName}
ORDER BY C.ORDINAL_POSITION
</select>
<select id="selectTableTypeColumnsInfo" parameterType="map" resultType="map">
SELECT
COLUMN_NAME
, INPUT_TYPE
, COLUMN_LABEL
, CODE_CATEGORY
, REFERENCE_TABLE
, REFERENCE_COLUMN
, DISPLAY_COLUMN
, IS_VISIBLE
, DISPLAY_ORDER
, DESCRIPTION
FROM TABLE_TYPE_COLUMNS
WHERE TABLE_NAME = #{tableName}
AND (COMPANY_CODE = #{companyCode} OR COMPANY_CODE = '*')
ORDER BY DISPLAY_ORDER NULLS LAST, COLUMN_NAME
</select>
</mapper>