데이터 변환
>> Web 상에서 GET/POST 방식으로 Server 쪽으로 값을 보내게 되면 ①데이터 변환 ②데이터 검증 단계를 거치게 된다.
>> 아래의 요청이 들어가면
URL?year=2022&month=6&day=18
>> ParameterMap 에 의해서 값들이 String으로 변환되고
>> WebDataBinder에 의하여 ①데이터 변환 ②데이터 검증 단계를 거쳐서
>> 변환하고자 하는 데이터 타입으로 변환되게 된다.
>> 타입변환에 대해서 알아보자
ParameterMap 에서 타입변환될때 보통 String 타입과, Integer 타입으로의 변환은 Spring에서 자동으로 변환해주지만
>> Date 타입의 변환이라던지, 내가 원하는 형식으로 변환할 경우는 직접 타입을 변환해주어야 한다. 그렇지 않으면 400에러가 발생한다.
>> 이때 변환하고자 하는 데이터 타입 뒤에 BindingResult 객체를 선언하면 에러는 발생하지 않고, Controller에서 그에 대한 처리를 어떻게 할지 우선권이 주어지게 된다.
>> 동일한 요청에 대해서 BindingResult 를 붙여준 후에는 에러가 발생하지 않고 해당 변환되지 못한 값만 null로 표현되는것을 확인할 수 있따.
>> 에러 창이 나오지 않은 것 뿐이지 console에 result를 찍어보면 1개의 에러가 발생한 것을 확인 할 수 있다.
>> BindingResult 의 참조변수인 result를 통해서 발생하는 에러의 갯수나 에러 형태등을 확인할 수 있다.
>> 이를 처리하기 위해서는 2가지 방법이 있다. 우선 첫번쨰 방법으로는
1. @InitBinder 를 통해서 해당 Controller로 들어오는 요청중 데이터 타입을 변환할 수 있다. 해당 애너테이션의 유효범위는 해당 컨트롤러 안에서만 유효하다.
1-1. DefaultPropertyEditor는 Spring에서 기본적으로 제공해주는 형태로 변환할수 있으며
1-2. CustomPropertyEditor는 사용자가 원하는 형태로 변환할 수 있다.
>> registerCustomEditor를 통해서 매개변수로 ("변환할 타입", PropertyEditor ) 가 들어가게되며
PropertyEditor의 종류는 아래의 주소를 통해서 확인할 수 있다.
해당 처리를 통해서
에러가 없어진것을 확인 할 수 있다.
이때 데이터를 변환할때 사용하는 것은 PropertyEditor만있는게 아니라
>> Converte (ConversionService), Formatter 를 통해서도 변환할 수 있다.
2번째 방법으로는 VO에서 처리해주는 방법으로 데이터 변환을 하고자 하는 값에 애너테이션을 붙여주는 방법이다.
>> DateTimeFormat은 String타입의 데이터를 pattern에서 정해준 형식으로Date 타입으로 변환을 해주고
>> NumberFormat은 String 타입의 데이터를 해당 pattern에 맞게 Integer 형식으로 바꿔준다.
Converter를 사용하기 위해서는 Converte를 구현해서 구현한 클래스를 등록해줘야 한다. 또한 Spring Bean으로 (@Configuration) 등록하여 사용가능하다.
이때 구현한 Converter를 통록하기 위해서 WebMvcConfigurer를 상속하여 addFormatters(FormatterRegistry registry) 를 오버라이드하여 추가해 줘야 한다.
>> Converter의 인자는 <1번째 인자를, 2번째 인자로 변경한다>라는 의미
public class ConverterClass{
public static class StringToIntegerConverter implements Converter<String, Integer>{
@Overide
public Integer conver(String source){
return new Integer(Integer.parseInt(source));
}
}
public static class IntegerToStringConverter implements Converter<Integer, String>{
@Overide
public String conver(Integer source){
return String.valueOf(source);
}
}
}
@Configuration
public class WebConfig implements WebMvcConfigurer{
@Overide
public void addFormatter(FornatterRegistry registry){
registry.addConverter(new ConverterClass.StringToIntegerConverter());
}
}
Formatter는 제네릭 인자로 1개를 받는데 이는 Object <-> String 간의 변환을 담당하기 떄문이다.
public class EventFormatter implements Formatter<Event> {
@Override
public Event parse(String text, Locale locale) throws ParseException {
return new Event(Integer.parseInt(text));
}
@Override
public String print(Event object, Locale locale) {
return object.getId().toString();
}
}
@Configurationpublic
class WebConfig implements WebMvcConfigurer {
@Override
public void addFormatters(FormatterRegistry registry) {
registry.addFormatter(new EventFormatter());
}
}
출처: https://engkimbs.tistory.com/738 [새로비:티스토리]
>> ConversionService는 Converter와 Formatter 인터페이스가 WebMvcConfigurer의 메서드를 통해서
ConversionService에 등록된다. ConversionService는 실제 데이터 변환이 일어나는 곳이며, 이
ConversionService를 통해 데이터 바인딩이 일어나게 된다.
>> ConversionService 의 참조변수를 출력해보면 등록되어있는 converter를 확인할 수 있다.
'dev > Spring' 카테고리의 다른 글
[Spring] form:form 태그 공부 (0) | 2022.06.19 |
---|---|
[Spring] 데이터 검증 (0) | 2022.06.18 |
[Spring] Spring MVC vs RESTful (0) | 2022.06.16 |
[Spring] 예외처리2 (0) | 2022.06.14 |
[Spring] 예외처리 (0) | 2022.06.13 |