스프링의 부가기능 | Validation과 Data Binding

Faithful Dev·2025년 2월 24일

스프링 프레임워크

목록 보기
8/20

Data Binding

Data Binding(데이터 바인딩)은 클라이언트에서 전달된 데이터를 컨트롤러의 매개변수나 객체에 자동으로 변환하여 주입하는 과정이다. 스프링 MVC에서는 @ModelAttribute, @RequestParam, @PathVariable, @RequestBody 등을 활용하여 데이터를 바인딩할 수 있다.

과정

  1. 클라이언트가 폼 데이터를 전송하거나 API 요청을 보냄.
  2. 스프링의 DataBinder가 요청 데이터를 컨트롤러의 매개변수 또는 객체에 매핑.
  3. 필드 타입이 맞지 않는 경우 예외 발생 (TypeMismatchException).
  4. 추가적인 검증(Validation)이 필요한 경우, Validator 또는 @Valid / @Validated를 사용하여 데이터 유효성 검사 진행.

예제

@PostMapping("/user")
public String createUser(@ModelAttribute UserDto userDto) {
	// userDto에 폼 데이터가 자동으로 바인딩됨
    return "success";
}

Validation

Validation(유효성 검사)은 바인딩된 데이터가 올바른 값인지 확인하는 과정이다. 스프링에서는 javax.validation@Valid, org.springframework.validation.annotation.Validated 등을 사용하여 유효성 검사를 수행할 수 있다.

방법

  1. 애노테이션 기반 유효성 검사 (@Valid, @Validated)
  2. Validator 인터페이스 활용 (Validator 구현)
  3. 컨트롤러에서 수동 검증 (BindingResult 활용)

애노테이션 기반 유효성 검사

스프링에서는 javax.validation.constraints 패키지의 애노테이션을 활용하여 유효성 검사를 할 수 있다.

@Valid를 사용한 유효성 검사

import jakarta.validation.constraints.*;

public class UserDto {
	@NotBlank(message = "이름은 필수 입력값입니다.")
    private String name;
    
    @Email(message = "올바른 이메일 형식이어야 합니다.")
    private String email;
    
    @Min(value = 18, message = "나이는 18세 이상이어야 합니다.")
    private int age;
}
@PostMapping("/user")
public String createUser(@Valid @ModelAttribute UserDto userDto, BindingResult bindingResult) {
	if (bindingResult.hasErrors()) {
    	return "error";
	}
    return "success";
}
  • @Valid는 DTO에 선언된 검증 애노테이션을 적용한다.
  • BindingResult를 활용하면 검증 오류가 발생했을 때 적절한 처리를 할 수 있다.

@Validated와 그룹별 검증

스프링에서 제공하는 @Validated를 사용하면 특정 그룹에 따라 검증 규칙을 다르게 적용할 수 있다.

검증 그룹 지정

public interface CreateGroup {}
public interface UpdateGroup {}

public class UserDto {
	@NotBlank(groups = CreateGroup.class, message = "이름은 필수 입력값입니다.")
    private String name;
    
    @Email(message = "올바른 이메일 형식이어야 합니다.")
    private String email;
    
    @Min(value = 18, groups = CreateGroup.class, message = "나이는 18세 이상이어야 합니다.")
    private int age;
}
@PostMapping("/user")
public String createUser(@Validated(CreateGroup.class) @RequestBody UserDto userDto, BindingResult bindingResult) {
	if (bindingResult.hasErrors()) {
    	return "error";
	}
    return "success";
}
  • @Validated(CreateGroup.class)를 사용하여 특정 검증 그룹을 적용할 수 있다.

Validator 인터페이스를 활용한 검증

Validator 인터페이스를 구현하면 커스텀한 검증 로직을 적용할 수 있다.

Validator 구현

import org.springframework.validation.Errors;
import org.springframework.validation.ValidationUtils;
import org.sprintframework.validation.Validator;

public class UserValidator implements Validator {
	@Override
    public boolean supports(Class<?> clazz) {
    	return UserDto.class.equals(clazz);
	}
    
    @Override
    public void validate(Object target, Errors errors) {
    	UserDto user = (UserDto) target;
        ValidationUtils.rejectIfEmptyOrWhitespace(errors, "name", "field.required", "이름은 필수 입력값입니다.");
        
        if (user.getAge() < 18) {
        	errors.rejectValue("age", "field.min", "나이는 18세 이상이어야합니다.");
		}
	}
}

컨트롤러에서 Validator 적용

@PostMapping("/user")
public String createUser(@ModelAttribute UserDto userDto, BindingResult bindingResult) {
	new UserValidator().validate(userDto, bindingResult);
    
    if (bindingResult.hasErrors()) {
    	return "error";
	}
    return "success";
}
  • 커스텀 검증 로직이 필요할 때 유용하게 사용할 수 있다.

글로벌 Validator 등록

스프링에서 WebDataBinder를 활용하여 Validator를 글로벌하게 등록할 수도 있다.

@ControllerAdvice
public class GlobalValidatorConfig {
	@InitBinder
    public void initBinder(WebDataBinder binder) {
    	binder.addValidators(new UserValidator());
	}
}
  • 모든 컨트롤러에서 UserValidator가 자동으로 실행된다.

정리

기능설명주요 애노테이션/클래스
Data Binding요청 데이터를 객체에 자동 매핑@ModelAttribute, @RequestParam, @RequestBody
기본 Validation애노테이션을 활용한 유효성 검사@Valid, @Validated, @NotBlank, @Email
그룹별 Validation그룹별로 유효성 검사를 적용@Validated(groups = GroupName.class)
커스텀 Validator직접 Validator를 구현하여 검증Validator 인터페이스
글로벌 Validator모든 컨트롤러에서 Validator 자동 적용@InitBinder, ControllerAdvice

이와 같이 스프링에서는 다양한 방식으로 데이터 바인딩과 검증을 수행할 수 있다.

profile
Turning Vision into Reality.

0개의 댓글