diff --git a/src/main/java/com/sniptext/domain/template/controller/TemplateController.java b/src/main/java/com/sniptext/domain/template/controller/TemplateController.java index 9a1e898..30ef031 100644 --- a/src/main/java/com/sniptext/domain/template/controller/TemplateController.java +++ b/src/main/java/com/sniptext/domain/template/controller/TemplateController.java @@ -1,6 +1,8 @@ package com.sniptext.domain.template.controller; import org.springframework.http.ResponseEntity; +import org.springframework.web.bind.annotation.GetMapping; +import org.springframework.web.bind.annotation.PathVariable; import org.springframework.web.bind.annotation.PostMapping; import org.springframework.web.bind.annotation.RequestBody; import org.springframework.web.bind.annotation.RequestMapping; @@ -8,8 +10,12 @@ import com.sniptext.domain.template.controller.dto.TemplateCreateRequest; import com.sniptext.domain.template.controller.dto.TemplateCreateResponse; +import com.sniptext.domain.template.controller.dto.TemplateDetailResponse; import com.sniptext.domain.template.service.TemplateCommandService; +import com.sniptext.domain.template.service.TemplateQueryService; +import com.sniptext.domain.template.service.dto.query.TemplateDetailQuery; import com.sniptext.domain.template.service.dto.result.TemplateCreateResult; +import com.sniptext.domain.template.service.dto.result.TemplateDetailResult; import com.sniptext.global.response.ApiResponse; import com.sniptext.global.security.LoginUser; @@ -25,6 +31,17 @@ public class TemplateController { private final TemplateCommandService templateCommandService; + private final TemplateQueryService templateQueryService; + + @GetMapping("/{templateId}") + public ResponseEntity> getTemplate( + @LoginUser Long userId, + @PathVariable Long templateId) { + + TemplateDetailResult result = templateQueryService.getTemplate(new TemplateDetailQuery(userId, templateId)); + + return ApiResponse.success(TemplateSuccessCode.TEMPLATE_FOUND, TemplateDetailResponse.from(result)); + } @PostMapping public ResponseEntity> createTemplate( diff --git a/src/main/java/com/sniptext/domain/template/controller/TemplateSuccessCode.java b/src/main/java/com/sniptext/domain/template/controller/TemplateSuccessCode.java index c9f7ed2..2b38d7a 100644 --- a/src/main/java/com/sniptext/domain/template/controller/TemplateSuccessCode.java +++ b/src/main/java/com/sniptext/domain/template/controller/TemplateSuccessCode.java @@ -11,6 +11,7 @@ @RequiredArgsConstructor public enum TemplateSuccessCode implements ResultCode { + TEMPLATE_FOUND(HttpStatus.OK, "TEMPLATE200_2", "템플릿 조회에 성공했습니다."), TEMPLATE_CREATED(HttpStatus.CREATED, "TEMPLATE201_1", "템플릿이 저장되었습니다."); private final HttpStatus httpStatus; diff --git a/src/main/java/com/sniptext/domain/template/controller/dto/TemplateDetailResponse.java b/src/main/java/com/sniptext/domain/template/controller/dto/TemplateDetailResponse.java new file mode 100644 index 0000000..e96b1f5 --- /dev/null +++ b/src/main/java/com/sniptext/domain/template/controller/dto/TemplateDetailResponse.java @@ -0,0 +1,33 @@ +package com.sniptext.domain.template.controller.dto; + +import java.time.LocalDateTime; +import java.util.List; + +import com.sniptext.domain.template.service.dto.result.TemplateDetailResult; + +/** 내 템플릿 상세 (명세 9번). 시각은 전역 직렬화 설정이 +09:00을 붙여 내보낸다. */ +public record TemplateDetailResponse( + Long templateId, + String title, + String shortcut, + String content, + List variables, + LocalDateTime lastUsedAt, + LocalDateTime createdAt, + LocalDateTime editedAt +) { + + public static TemplateDetailResponse from(TemplateDetailResult result) { + return new TemplateDetailResponse( + result.templateId(), + result.title(), + result.shortcut(), + result.content(), + result.variables(), + result.lastUsedAt(), + result.createdAt(), + result.editedAt() + ); + } + +} diff --git a/src/main/java/com/sniptext/domain/template/exception/TemplateErrorCode.java b/src/main/java/com/sniptext/domain/template/exception/TemplateErrorCode.java index 5c9fc03..36345df 100644 --- a/src/main/java/com/sniptext/domain/template/exception/TemplateErrorCode.java +++ b/src/main/java/com/sniptext/domain/template/exception/TemplateErrorCode.java @@ -30,6 +30,10 @@ public enum TemplateErrorCode implements ResultCode { CONTENT_TOO_LONG(HttpStatus.BAD_REQUEST, "TEMPLATE400_7", "템플릿 내용은 3,000자까지 입력할 수 있어요."), /** 활성 템플릿 수가 플랜 한도 이상 (화면은 한도 모달) */ TEMPLATE_LIMIT_REACHED(HttpStatus.FORBIDDEN, "TEMPLATE403_1", "템플릿 저장 한도에 도달했어요."), + /** 없는 템플릿, 다른 회원의 템플릿 (다른 회원의 휴지통 템플릿 포함) */ + TEMPLATE_NOT_FOUND(HttpStatus.NOT_FOUND, "TEMPLATE404_1", "템플릿을 찾을 수 없어요."), + /** 내 템플릿인데 휴지통에 있음 */ + TEMPLATE_IN_TRASH(HttpStatus.NOT_FOUND, "TEMPLATE404_2", "이미 삭제된 템플릿이에요."), /** 내 템플릿(휴지통 제외)에 같은 단축어 키가 있음. 대소문자 무시 */ SHORTCUT_DUPLICATED(HttpStatus.CONFLICT, "TEMPLATE409_1", "이미 사용 중인 단축어예요."), /** 자동 번호 2~99가 모두 사용 중 (갤러리 저장·휴지통 복구) */ diff --git a/src/main/java/com/sniptext/domain/template/repository/TemplateRepository.java b/src/main/java/com/sniptext/domain/template/repository/TemplateRepository.java index 97badfe..0000b76 100644 --- a/src/main/java/com/sniptext/domain/template/repository/TemplateRepository.java +++ b/src/main/java/com/sniptext/domain/template/repository/TemplateRepository.java @@ -3,6 +3,7 @@ import java.time.LocalDateTime; import java.util.Collection; import java.util.List; +import java.util.Optional; import java.util.Set; import org.springframework.data.domain.Limit; @@ -15,6 +16,9 @@ public interface TemplateRepository extends JpaRepository { + /** 본인 소유 조회. 휴지통 템플릿도 찾으므로 내 휴지통과 다른 회원 것을 호출자가 구분할 수 있다 */ + Optional