soft IT life

kotlin+springboot 환경에서 @Valid 적용 되지 않는 이슈 본문

Errors

kotlin+springboot 환경에서 @Valid 적용 되지 않는 이슈

softPattern 2024. 4. 9. 17:48

[Kotlin, SpringBoot로 웹 서비스 개발, 기능 테스트 중에 유효성 검사 처리가 제대로 적용되지 않는 이슈 발생]

@PatchMapping("/{activityResultKey}/evaluation")
fun editAssignmentEvaluation(
    @Valid @RequestBody data: AssignmentEvaluationDTO,
)
data class AssignmentEvaluationDTO(
    @field:NotNull(message = "평가점수는 필수 항목입니다.")
    @Min(value = 0, message = "평가점수는 0 이상의 값이어야 합니다.")
    @Max(value = 100, message = "평가점수는 100 이하의 값이어야 합니다.")
    val score: Int,
    @field:NotBlank(message = "평가내용은 필수 항목입니다.")
    val comment: String,
)

 

What

위와 같이 Controller에서 @Valid 어노테이션(jakarta.validation 패키지)을 RequestBody에 붙이고

 

DTO내에서도 Validation을 올바르게 사용하였다고 생각하며 기능을 작동중이었는데

 

계속 NotNull, NotBlank validation 처리만 정상적으로 되고 'score'필드의 값 범위 validation에 대해선 전혀 적용되지 않고 있었다.

 

 

Why?

이유는 단순했다. annotaion 사용시에 Annotation Target(해당 annotation을 어떤 요소에 붙일 것인지 명시하는 것)을 명확히 명시해주지 않은것!

 

(annotation 사용시에 어느 Target에 적용시킬지 정확히 코드에 작성해주지 않으면 제대로 인식하지 못하는 문제인 것 같다.)

 

위 코드를 보면 알수잇듯이, 나는 Min과 Max 어노테이션에는 어느 target인지 명시해주지 않았고

 

해당 annotaion이 제대로 작동하지 않은 것이었다.

 

Annotation Tager => field이므로 아래와 같이 어노테이션 시작시에 '@field:' 키워드를 append 해주어야 한다.

data class AssignmentEvaluationDTO(
    @field:NotNull(message = "평가점수는 필수 항목입니다.")
    @field:Min(value = 0, message = "평가점수는 0 이상의 값이어야 합니다.")
    @field:Max(value = 100, message = "평가점수는 100 이하의 값이어야 합니다.")
    val score: Int,
    @field:NotBlank(message = "평가내용은 필수 항목입니다.")
    val comment: String,
)

 

이렇게 수정하여 작동시키면 정상적으로 내가 원하는 유효성 검사가 진행되며 예외 처리로 막히는 것을 확인하였다.

 

 

cf) 해당 요소에 다른 target을 명시하면 어떻게 될까 ?

 

cf) kotlin의 Annotation Target 종류

package kotlin.annotation

import kotlin.annotation.AnnotationTarget.*

/**
 * Contains the list of code elements which are the possible annotation targets
 */
public enum class AnnotationTarget {
    /** Class, interface or object, annotation class is also included */
    CLASS,
    /** Annotation class only */
    ANNOTATION_CLASS,
    /** Generic type parameter */
    TYPE_PARAMETER,
    /** Property */
    PROPERTY,
    /** Field, including property's backing field */
    FIELD,
    /** Local variable */
    LOCAL_VARIABLE,
    /** Value parameter of a function or a constructor */
    VALUE_PARAMETER,
    /** Constructor only (primary or secondary) */
    CONSTRUCTOR,
    /** Function (constructors are not included) */
    FUNCTION,
    /** Property getter only */
    PROPERTY_GETTER,
    /** Property setter only */
    PROPERTY_SETTER,
    /** Type usage */
    TYPE,
    /** Any expression */
    EXPRESSION,
    /** File */
    FILE,
    /** Type alias */
    @SinceKotlin("1.1")
    TYPEALIAS
}