주니 개발 도서관

Spring boot

[ Spring boot ] Validator ( 유효성 검사 )

주니홍 2022. 10. 26. 14:21

 

[ Validator ]


사용자가 보낸 데이터(  = 폼 데이터 ) 유효성 검사
이 유효성 검사는 " 두 단계 "로 진행하는 것이 보편적임

1. 클라이언트 ( 브라우저, 사용자) : JS

2. 서버 : 파라미터 값을 검증

 

클라이언트에서 유효성검사가 가능하지만 100% 모두 막을 순 없다

그렇기 때문에 두 단계로 서버에서도 유효성 검사를 해주는 것이 보편적이다

 

회사마다 유효성검사다 다르기 때문에 유지보수에 좋지않다

하지만, 스프링에서는 Validator 인터페이스를 구현해놓음

>> 개발자들이 보다 일관된 코드를 작성할 수 있게됨

 


 

Validator를 이용하기위해 한번 DTO ** , Validator, Controller 를 생성

 

 

DTO(Data Transfer Object) 란 내가 사용했던 VO의 역할을 가진 클래스이다.

 

VO(Value Object)는 getter만 가지고 있는 값 오브젝트로써 값을 위해 쓰입니다.

read-Only 특징(사용하는 도중에 변경 불가능하며 오직 읽기만 가능)을 가집니다.

 

DTO와 유사하지만 DTO는 setter를 가지고 있어 값이 변할 수 있습니다.

( 사실상 현재까지 사용한 VO역할이 DTO의 역할 이였던 것 )

 

DataValidator 클래스는 유효성검사를 위한 클래스이다

 


 

커맨드 객체로 사용할 DTO에는 id, writer, content가 존재한다 (+ getter & setter )

 

 

유효성검사를 해줄 DataValidator 클래스

Spring framework 에서 제공** 하는 Validator를 implements 하여 사용한다

 

인터페이스를 불러왔기때문에 Override된 메서드를 확인해보자

supports() 메서드는 따로 건들지 않는다고 한다

 

중점으로 사용할 validate() 메서드를 확인해보자

 

인자(파라미터)로 Object가 있다면 어떤 데이터가 올지 모르는 것
Object target : 사용자의 입력 값(커맨드 객체)을 검증하기위해, 파라미터로 받을 수 있게 구현한 부분
ex) 디자인 패턴을 활용한 예 : 부모에게 자식을 대입 가능한것 처럼 Object를 이용한 것

 

 

 

어떤객체가 올지 모르기때문에 instanceof를 이용하여 커맨드 객체와 동일한지 확인해야한다

현재는 DataDTO만 사용하고 있기때문에 따로 추가하지 않았다

Member나 Board 등등 다른 DTO가 존재한다면 instanceof로 하나하나 비교해주고

instanceof로 확인한 조건문 내부에서 커맨드객체에 맞는 형변환을 해주어야 할 것이다

 

 

 

DTO에서 Writer와 Content를 꺼내어 유효성검사를 실시한다

 

** if ( writer.trim().isEmpty() || writer == null ) 중요 오류

만약 조건을 위와같이 설정하였다면 오류가 발생한다

writer가 null일 경우 isEmpty()를 실행할 수 없기때문이다 

 

그래서 werter == null 인지 먼저 조건을 확인해야 한다

 

trim()과 같이 빈(공백) 값 혹은 Null을 다루는 관련 내용을 참조한 블로그이다

( isBlank()를 활용해 보는것도 좋을 것 같다 )

 

https://hianna.tistory.com/530

 

[Java] String(문자열) 빈 값 체크하기 (null, 공백)

문자열(String)이 null 또는 빈 공백인지 체크하는 방법을 소개합니다. 1. isEmpty() - Java 6 이상 isEmpty() 코드  public class StringEmptyCheck { public static void main(String[] args) { String str1 =..

hianna.tistory.com

 

** &&, || 연산자의 특성을 잘 생각해야 한다

&& 일경우 모두 true여야 하고
|| 일경우 하나만 true여도 통과이다

&& 일경우 앞의 조건이 false라면 뒤의 조건은 보지않는다
= 어차피 false가 있기때문에 &&는 무조건 false가 된다 그렇기때문에 뒤의 조건을 보지않는다

|| 일경우도 마찬가지로 앞의 조건이 true라면 뒤의 조건은 보지않는다
= 어차피 true가 있기때문에 || 는 무조건 true가 된다 그렇기때문에 뒤의 조건을 보지않는다

 

System.out.println 으로 로그를 남기고

validate() 인자로 errors를 가지고있는데 이는 참조형 변수이다 ( Model model 객체같은 형식 )

errors.rejectValue( "어떤파트" ,  "어떤에러" )를 통해 에러내용을 저장한다

 

Q. errors 객체에 에러 내용을 저장했는데, validate() 메서드는 별도의 return을 하지않음
validate() 메서드를 수행할때에, errors 객체를 참조형변수로 활용하기 때문!
>> 모델 객체, 커맨드 객체처럼 저장되기 때문

 

 


Controller에서 받아오는 값을 이용하여 유효성검사를 해보겠습니다

 

@ModelAttribute("dto") DataDTO dto ( 커맨드 객체 ) +

Errors객체를 만들어준 인터페이스객체인 BindingResult객체를 인자로 넣습니다

 

** @ModelAttribute("dto") 의미

행여나 실수로 작성자를 적지않고 내용만 500자이상 적었을시

작성자가 null이기 때문에 오류가 발생한다

이때 내용을 저장하고 있지 않는다면 내용이 초기화가 되기 때문에

@ModelAttribute("dto")를 이용하여 커맨드객체로 가져올때 저장할 수 있게된다

 

BindingResult객체는 인터페이스인데 Errors객체로서 인자에 담을 수 있다

 

28번라인을 통해 DataValidator클래스를 new 객체로 생성하고

31번라인을 통해 validate ( dto , result ) 메서드인자로 넣어서 보내주면 아래 메서드가 실행된다

 

DataValidator.java  validate() 내부

Object target = DataDTO객체

Errors errors = BindingResult객체 ( = Errors의 인터페이스라서 가능)

 

validate() 메서드 내부에서 유효성검사를 거치고 저장된 에러를

33번라인 조건문 result.hasErrors() 를 통해 저장된 에러가 있는지 확인할 수있다

= 존재한다면 true를 반환

 

존재한다면 다시 작성할 수 있도록 return 페이지를 담고있는 viewName변수에  insertPage로 설정

( 디폴트값으로 변수 생성시 처음에 BoardPage로 설정 )

 

그리고 리턴하여 페이지로 이동한다

 

**  validate() 메서드 내부에서 Errors객체는 Model객체처럼 저장이 된다 ( = 참조형 변수 )

validate() 메서드가 종료되어 result.hasErrors()통해 저장된 에러가 있는지 확인하는데

/insert 요청에 의해 메서드가 호출되었을경우 컨테이너가 result 객체를 매번 새로 만들어 준다

그렇기 때문에 Errors에 저장된 내용이 초기화(리셋)되는 것이였고

이를 컨테이너가 관리해 주고 있었던 것이다.

( 만약 항상 초기화(리셋)해주지 않았다면 hasErrors()를 항상 통과 할 것이기 때문에 )

 


 

insertPage.jsp

사용자에게 작성자와 내용을 받아올 수 있다

 

 

내용이 존재하지 않을 경우

 

 

작성자가 존재하지 않을경우

 

 

작성자와 내용 둘다 존재하지 않을경우

 

 

 

boardPage.jsp

 

insertPage에서 알맞게 작성자와 내용을 채웟다면

boardPage.jsp로 이동하며 위 처럼 출력해 준다

 

 

 

 

'Spring boot' 카테고리의 다른 글

[ Spring Boot ] 트랜잭션  (0) 2022.11.01
[ Spring boot ] JDBCTemplate  (2) 2022.10.27
[ Spring Boot ] 부트 웹 기초  (0) 2022.10.25
[ Spring boot ] 의존 주입  (0) 2022.10.24
[ Spring Boot ] 다운로드 및 설정  (0) 2022.10.24