에러 메세지
Spring의 Bean Validation은 Default로 제공하는 Message들이 존재하고 임의로 수정할 수 있다.
BindingResult에 등록된 검증 오류를 확인해보면 오류가 Annotation 이름으로 등록되어 있다.@Data
public class TestDto {
@NotBlank
private String stringField;
@NotNull
@Range(min = 1, max = 9999)
private Integer integerField;
}
@Slf4j
@RestController
public class BeanValidationController {
@PostMapping("/error-message")
public String beanValidation(
@Validated @ModelAttribute TestDto dto,
BindingResult bindingResult
) {
// bindingResult Field Error 출력
if (bindingResult.hasErrors()) {
return String.valueOf(bindingResult.getFieldError());
}
// 성공시 문자열 반환
return "회원가입 성공";
}
}


integerField 는 비워두고 stringField 만 값(”문자열”) 입력 Field error in object 'testDto' on field 'integerField': rejected value [null]; codes [NotNull.testDto.integerField,NotNull.integerField,NotNull.java.lang.Integer,NotNull]; arguments [org.springframework.context.support.DefaultMessageSourceResolvable: codes [testDto.integerField,integerField]; arguments []; default message [integerField]]; default message [널이어서는 안됩니다] ```
MessageCodesResolver 를 통해 메세지 코드 생성Spring 에서는 오류 메시지 코드관리를 위해 MessageCodesResolver 인터페이스의
구현체인 DefaultMessageCodesResolver를 기본으로 사용한다.
message 속성 사용@Data
public class TestDto {
@NotBlank(message = "메세지 수정 가능")
private String stringField;
}

MessageSource란 Spring에서 지원하는 인터페이스로 메세지의 국제화를 위해 사용된다.
Object Error
필드 단위가 아닌 객체 전체에 대한 오류를 나타낸다. 예를들어 두 필드 간의 관계를 검증할 때 ObjectError를 통해 해당 오류를 BindingResult에 기록할 수 있다.
@ScriptAssert
비밀번호와 비밀번호 확인 필드가 동일한지 검증
@Data
@ScriptAssert(lang = "javascript", script = "_this.password === _this.confirmPassword", message = "Passwords do not match")
public class UserRegistrationDto {
@NotBlank(message = "Password is required")
private String password;
@NotBlank(message = "Confirm password is required")
private String confirmPassword;
}
실제로 @ScriptAssert는 제약사항 때문에 사용하지 않는다.
실무에서는 훨씬 복잡한 Validation들이 필요하지만 대응이 불가능하다.
ex) 다른 객체끼리의 비교 혹은 DB조회 결과와 비교
Object Error의 경우 Java 코드로 직접 Validation 한다.
Java 코드로 구현하기
price * count ≥ 10000
@Getter
@AllArgsConstructor
public class OrderRequestDto {
@NotNull
@Range(min = 1000)
private Integer price;
@NotNull
@Range(min = 1)
private Integer count;
}
@Slf4j
@RestController
public class BeanValidationController {
@PostMapping("/object-error")
public String objectError(
@Validated @ModelAttribute OrderRequestDto requestDto,
BindingResult bindingResult
) {
// 합이 10000원 이상인지 확인
int result = requestDto.getPrice() * requestDto.getCount();
if (result < 10000) {
// Object Error
bindingResult.reject("totalMin", new Object[]{10000, result}, "총 합이 10000 이상이어야 합니다.");
}
// Error가 있으면 출력
if (bindingResult.hasErrors()) {
log.info("errors={}", bindingResult);
return bindingResult.getAllErrors().get(0).getDefaultMessage();
}
// 성공로직 ...
return "성공";
}
}
Object Error는 로직으로 구현하면 된다.
Postman

@ModelAttribute는 기본 생성자만 있을 때는 setter를 통해 파라미터를 바인딩하고 다른 매개변수를 가진 생성자가 있다면 그 생성자를 이용해서 파라미터 바인딩을 수행한다.