diff --git a/src/main/java/com/bio/bio_backend/domain/admin/common_code/controller/CommonCodeController.java b/src/main/java/com/bio/bio_backend/domain/admin/common_code/controller/CommonCodeController.java index 30866df..3c20852 100644 --- a/src/main/java/com/bio/bio_backend/domain/admin/common_code/controller/CommonCodeController.java +++ b/src/main/java/com/bio/bio_backend/domain/admin/common_code/controller/CommonCodeController.java @@ -168,8 +168,8 @@ public class CommonCodeController { @ApiResponse(responseCode = "404", description = "공통 코드를 찾을 수 없음", content = @Content(schema = @Schema(implementation = ApiResponseDto.class))) }) @GetMapping("/{code}") - public ResponseEntity> getCode(@PathVariable String code) { - CommonCodeDto commonCode = commonCodeService.getCode(code); + public ResponseEntity> getCode(@PathVariable String code) { + GetCommonCodeResponseDto commonCode = commonCodeService.getCodeWithJoinInfo(code); return ResponseEntity.ok(ApiResponseDto.success(ApiResponseCode.COMMON_SUCCESS_RETRIEVED, commonCode)); } diff --git a/src/main/java/com/bio/bio_backend/domain/admin/common_code/dto/GetCommonCodeResponseDto.java b/src/main/java/com/bio/bio_backend/domain/admin/common_code/dto/GetCommonCodeResponseDto.java new file mode 100644 index 0000000..3731928 --- /dev/null +++ b/src/main/java/com/bio/bio_backend/domain/admin/common_code/dto/GetCommonCodeResponseDto.java @@ -0,0 +1,68 @@ +package com.bio.bio_backend.domain.admin.common_code.dto; + +import jakarta.persistence.*; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; + +import java.time.LocalDateTime; + +/** + * 공통 코드 조회용 Response DTO + * CommonGroupCode의 name과 Member의 name을 join을 통해 함께 조회 + */ +@Data +@Builder +@NoArgsConstructor +@AllArgsConstructor +@SqlResultSetMapping( + name = "GetCommonCodeResponseDtoMapping", + classes = @ConstructorResult( + targetClass = GetCommonCodeResponseDto.class, + columns = { + @ColumnResult(name = "code", type = String.class), + @ColumnResult(name = "name", type = String.class), + @ColumnResult(name = "description", type = String.class), + @ColumnResult(name = "group_code", type = String.class), + @ColumnResult(name = "parent_code", type = String.class), + @ColumnResult(name = "character_ref1", type = String.class), + @ColumnResult(name = "character_ref2", type = String.class), + @ColumnResult(name = "character_ref3", type = String.class), + @ColumnResult(name = "character_ref4", type = String.class), + @ColumnResult(name = "character_ref5", type = String.class), + @ColumnResult(name = "sort_order", type = Integer.class), + @ColumnResult(name = "use_flag", type = Boolean.class), + @ColumnResult(name = "created_at", type = LocalDateTime.class), + @ColumnResult(name = "updated_at", type = LocalDateTime.class), + @ColumnResult(name = "group_code_name", type = String.class), + @ColumnResult(name = "created_by_name", type = String.class), + @ColumnResult(name = "updated_by_name", type = String.class) + } + ) +) +public class GetCommonCodeResponseDto { + + // CommonCode 기본 정보 + private String code; + private String name; + private String description; + private String groupCode; + private String parentCode; + private String characterRef1; + private String characterRef2; + private String characterRef3; + private String characterRef4; + private String characterRef5; + private Integer sortOrder; + private Boolean useFlag; + + // BaseEntity 정보 + private LocalDateTime createdAt; + private LocalDateTime updatedAt; + + // Join을 통해 가져올 정보 + private String groupCodeName; // CommonGroupCode의 name + private String createdByName; // 생성자 Member의 name + private String updatedByName; // 수정자 Member의 name +} diff --git a/src/main/java/com/bio/bio_backend/domain/admin/common_code/repository/CommonCodeRepositoryCustom.java b/src/main/java/com/bio/bio_backend/domain/admin/common_code/repository/CommonCodeRepositoryCustom.java index 240a837..573a540 100644 --- a/src/main/java/com/bio/bio_backend/domain/admin/common_code/repository/CommonCodeRepositoryCustom.java +++ b/src/main/java/com/bio/bio_backend/domain/admin/common_code/repository/CommonCodeRepositoryCustom.java @@ -1,7 +1,9 @@ package com.bio.bio_backend.domain.admin.common_code.repository; +import com.bio.bio_backend.domain.admin.common_code.dto.GetCommonCodeResponseDto; import com.bio.bio_backend.domain.admin.common_code.entity.CommonCode; import java.util.List; +import java.util.Optional; /** * QueryDSL을 활용한 커스텀 쿼리 메서드들을 정의하는 인터페이스 @@ -24,4 +26,22 @@ public interface CommonCodeRepositoryCustom { * @return List 활성화된 공통 코드 목록 */ List findByParentCode(String parentCode); + + /** + * 특정 공통 코드를 조회하며 CommonGroupCode와 Member 정보를 join하여 함께 조회합니다. + * QueryDSL을 사용하여 성능 최적화된 쿼리를 실행합니다. + * + * @param code 조회할 공통 코드 + * @return Optional 조회된 공통 코드 정보 (없으면 empty) + */ + Optional findCodeWithJoinInfo(String code); + + /** + * 특정 공통 코드를 조회하며 CommonGroupCode와 Member 정보를 join하여 함께 조회합니다. + * Native Query를 사용한 버전 (사용하지 않음, 참고용) + * + * @param code 조회할 공통 코드 + * @return Optional 조회된 공통 코드 정보 (없으면 empty) + */ + Optional findCodeWithJoinInfoNative(String code); } \ No newline at end of file diff --git a/src/main/java/com/bio/bio_backend/domain/admin/common_code/repository/CommonCodeRepositoryImpl.java b/src/main/java/com/bio/bio_backend/domain/admin/common_code/repository/CommonCodeRepositoryImpl.java index bf9a279..77314cf 100644 --- a/src/main/java/com/bio/bio_backend/domain/admin/common_code/repository/CommonCodeRepositoryImpl.java +++ b/src/main/java/com/bio/bio_backend/domain/admin/common_code/repository/CommonCodeRepositoryImpl.java @@ -1,12 +1,18 @@ package com.bio.bio_backend.domain.admin.common_code.repository; +import com.bio.bio_backend.domain.admin.common_code.dto.GetCommonCodeResponseDto; import com.bio.bio_backend.domain.admin.common_code.entity.CommonCode; import com.bio.bio_backend.domain.admin.common_code.entity.QCommonCode; +import com.bio.bio_backend.domain.admin.common_code.entity.QCommonGroupCode; +import com.bio.bio_backend.domain.base.member.entity.QMember; +import com.querydsl.core.types.Projections; import com.querydsl.jpa.impl.JPAQueryFactory; +import jakarta.persistence.EntityManager; import lombok.RequiredArgsConstructor; import org.springframework.stereotype.Repository; import java.util.List; +import java.util.Optional; /** * QueryDSL을 활용하여 CommonCodeRepositoryCustom 인터페이스를 구현하는 클래스 @@ -17,12 +23,16 @@ import java.util.List; public class CommonCodeRepositoryImpl implements CommonCodeRepositoryCustom { private final JPAQueryFactory queryFactory; + private final EntityManager entityManager; /** - * QCommonCode 인스턴스를 생성하여 쿼리에서 사용합니다. + * Q클래스 인스턴스들을 생성하여 쿼리에서 사용합니다. * QueryDSL의 Q클래스를 통해 타입 안전한 쿼리 작성이 가능합니다. */ private final QCommonCode commonCode = QCommonCode.commonCode; + private final QCommonGroupCode commonGroupCode = QCommonGroupCode.commonGroupCode; + private final QMember createdByMember = new QMember("createdByMember"); + private final QMember updatedByMember = new QMember("updatedByMember"); @Override public List findByGroupCode(String groupCode) { @@ -43,4 +53,53 @@ public class CommonCodeRepositoryImpl implements CommonCodeRepositoryCustom { .orderBy(commonCode.sortOrder.asc()) .fetch(); } + + @Override + public Optional findCodeWithJoinInfo(String code) { + return Optional.ofNullable( + queryFactory + .select(Projections.constructor(GetCommonCodeResponseDto.class, + commonCode.code, commonCode.name, commonCode.description, + commonCode.groupCode, commonCode.parentCode, + commonCode.characterRef1, commonCode.characterRef2, commonCode.characterRef3, + commonCode.characterRef4, commonCode.characterRef5, + commonCode.sortOrder, commonCode.useFlag, + commonCode.createdAt, commonCode.updatedAt, + commonGroupCode.name, createdByMember.name, updatedByMember.name + )) + .from(commonCode) + .leftJoin(commonGroupCode).on(commonCode.groupCode.eq(commonGroupCode.code)) + .leftJoin(createdByMember).on(commonCode.createdOid.eq(createdByMember.oid)) + .leftJoin(updatedByMember).on(commonCode.updatedOid.eq(updatedByMember.oid)) + .where(commonCode.code.eq(code)) + .fetchOne() + ); + } + + @Override + public Optional findCodeWithJoinInfoNative(String code) { + String nativeQuery = """ + SELECT cc.code, cc.name, cc.description, cc.group_code, cc.parent_code, + cc.character_ref1, cc.character_ref2, cc.character_ref3, cc.character_ref4, cc.character_ref5, + cc.sort_order, cc.use_flag, cc.created_at, cc.updated_at, + cgc.name as group_code_name, cm1.name as created_by_name, cm2.name as updated_by_name + FROM st_common_code cc + LEFT JOIN st_common_group_code cgc ON cc.group_code = cgc.code + LEFT JOIN st_member cm1 ON cc.created_oid = cm1.oid + LEFT JOIN st_member cm2 ON cc.updated_oid = cm2.oid + WHERE cc.code = :code + """; + + try { + @SuppressWarnings("unchecked") + List results = entityManager + .createNativeQuery(nativeQuery, "GetCommonCodeResponseDtoMapping") + .setParameter("code", code) + .getResultList(); + + return results.isEmpty() ? Optional.empty() : Optional.of(results.get(0)); + } catch (Exception e) { + return Optional.empty(); + } + } } diff --git a/src/main/java/com/bio/bio_backend/domain/admin/common_code/service/CommonCodeService.java b/src/main/java/com/bio/bio_backend/domain/admin/common_code/service/CommonCodeService.java index 561485c..348f629 100644 --- a/src/main/java/com/bio/bio_backend/domain/admin/common_code/service/CommonCodeService.java +++ b/src/main/java/com/bio/bio_backend/domain/admin/common_code/service/CommonCodeService.java @@ -2,6 +2,7 @@ package com.bio.bio_backend.domain.admin.common_code.service; import com.bio.bio_backend.domain.admin.common_code.dto.CommonCodeDto; import com.bio.bio_backend.domain.admin.common_code.dto.CommonGroupCodeDto; +import com.bio.bio_backend.domain.admin.common_code.dto.GetCommonCodeResponseDto; import java.util.List; @@ -20,6 +21,7 @@ public interface CommonCodeService { void updateCode(String code, CommonCodeDto codeDto); void deleteCode(String code); CommonCodeDto getCode(String code); + GetCommonCodeResponseDto getCodeWithJoinInfo(String code); List getActiveCodesByGroupCode(String groupCode); List getActiveCodesByParentCode(String parentCode); List getAllCodes(); diff --git a/src/main/java/com/bio/bio_backend/domain/admin/common_code/service/CommonCodeServiceImpl.java b/src/main/java/com/bio/bio_backend/domain/admin/common_code/service/CommonCodeServiceImpl.java index 57d32cb..a5b0b32 100644 --- a/src/main/java/com/bio/bio_backend/domain/admin/common_code/service/CommonCodeServiceImpl.java +++ b/src/main/java/com/bio/bio_backend/domain/admin/common_code/service/CommonCodeServiceImpl.java @@ -2,6 +2,7 @@ package com.bio.bio_backend.domain.admin.common_code.service; import com.bio.bio_backend.domain.admin.common_code.dto.CommonCodeDto; import com.bio.bio_backend.domain.admin.common_code.dto.CommonGroupCodeDto; +import com.bio.bio_backend.domain.admin.common_code.dto.GetCommonCodeResponseDto; import com.bio.bio_backend.domain.admin.common_code.entity.CommonCode; import com.bio.bio_backend.domain.admin.common_code.entity.CommonGroupCode; import com.bio.bio_backend.domain.admin.common_code.mapper.CommonCodeMapper; @@ -133,6 +134,12 @@ public class CommonCodeServiceImpl implements CommonCodeService { return commonCodeMapper.toCommonCodeDto(commonCode); } + @Override + public GetCommonCodeResponseDto getCodeWithJoinInfo(String code) { + return commonCodeRepository.findCodeWithJoinInfo(code) + .orElseThrow(() -> new ApiException(ApiResponseCode.COMMON_CODE_ERROR_003)); + } + @Override public List getActiveCodesByGroupCode(String groupCode) { List commonCodes = commonCodeRepository.findByGroupCode(groupCode);