Spring/Boot
[Boot] Validation
hvoon
2022. 9. 10. 20:48
Validation: null, 빈 값인지 검증하는 Annotation
src\main\java\com\ecl\g06\
package com.ecl.g06;
import lombok.Data;
@Data
public class ContentDto {
private String writer;
private String content;
}
package com.ecl.g06;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
@Controller
public class ValidController {
@RequestMapping("/")
public String main() {
return "startPage";
}
}
src\main\webapp\WEB-INF\views\startPage.jsp
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>startPage.jsp</title>
</head>
<body>
<form action="create">
작성자 : <input type="text" name="writer" value="${dto.writer}"> <br />
내용 : <input type="text" name="content" value="${dto.content}"> <br />
<input type="submit" value="전송"> <br />
${message }
</form>
</body>
</html>
src\main\java\com\ecl\g06\
package com.ecl.g06;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.ModelAttribute;
import org.springframework.web.bind.annotation.RequestMapping;
@Controller
public class ValidController {
@RequestMapping("/")
public String main() {
return "startPage";
}
@RequestMapping("/create")
// startPage.jsp에서 form action="create"
public String create(
@ModelAttribute("dto") ContentDto contentdto, Model model) {
// 전송된 값들을 검사해서 한 개의 값이라도 비어 있으면 startPage.jsp로 되돌아감
// 이 때 전송된 값을 저장하고 있는 contentdto 객체는
// dto란 이름으로 model에 담겨져서 이동
// validation 기능이 있는 클래스를 생성하고 그 객체를 이용해서 검사함
// 클래스의 이름은 ContentValidator,
// java의 Validator 인터페이스를 implements 한 클래스
ContentValidator valid = new ContentValidator();
}
}
package com.ecl.g06;
import org.springframework.validation.Errors;
import org.springframework.validation.Validator;
public class ContentValidator implements Validator{
@Override
public boolean supports(Class<?> clazz) { // 거의 사용할 일 없음
return false;
}
@Override
public void validate(Object target, Errors errors) {
// Object target: 검사할 객체를 받아주는 매개변수(Object형).
// 전달된 객체 내의 멤버변수가 비어있는지 검사 예정
// Errors errors: 보내온 객체에 에러내용을 담아서
}
}
package com.ecl.g06;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.validation.BindingResult;
import org.springframework.web.bind.annotation.ModelAttribute;
import org.springframework.web.bind.annotation.RequestMapping;
@Controller
public class ValidController {
@RequestMapping("/")
public String main() {
return "startPage";
}
@RequestMapping("/create")
// startPage.jsp에서 form action="create"
public String create(
@ModelAttribute("dto") ContentDto contentdto, Model model,
BindingResult result) {
ContentValidator valid = new ContentValidator();
valid.validate(contentdto, result);
// BindingResult result: 에러 제목(키 값)과 내용(밸류값)을 담을 수 있는 객체
// validator의 멤버메서드인 validate가 contentdto 내용을 검사한 후
// result에 오류 내용을 담아주고 리턴되지 않아도 call by reference이기 때문에
// 오류 내용을 현재 위치에서도 result라는 이름으로 사용 가능함
if (result.hasErrors()) {
model.addAttribute("message","writer와 content는 비어 있으면 안됨");
return "startPage";
}else {
return "DonePage";
}
}
}
package com.ecl.g06;
import org.springframework.validation.Errors;
import org.springframework.validation.Validator;
public class ContentValidator implements Validator{
@Override
public boolean supports(Class<?> clazz) {
return false;
}
@Override
public void validate(Object target, Errors errors) {
ContentDto dto = (ContentDto)target;
String sWriter = dto.getWriter();
String sContent = dto.getContent();
// null(new String()조차도 실행 안된것)이거나 값이 비어있거나("")
if (sWriter==null || sWriter.trim().isEmpty()) {
System.out.println("Writer is null or empty");
errors.rejectValue("writer", "trouble");
}
if (sContent==null || sContent.trim().isEmpty()) {
System.out.println("Content is null or empty");
errors.rejectValue("content", "trouble");
}
}
}
src\main\webapp\WEB-INF\views\DonePage.jsp
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>DonePage.jsp</title>
</head>
<body>
<h1>startPage.jsp에서 DonePage.jsp로 전달된 내용</h1>
<h1>이름: ${dto.writer }</h1>
<h1>내용: ${dto.content }</h1>
</body>
</html>


전달 객체의 멤버 변수를 꺼내어 보지 않고 null이거나 비어 있는지 점검
(ValidationUtils.rejectIfEmptyOrWhitespace)
package com.ecl.g07;
import org.springframework.validation.Errors;
import org.springframework.validation.ValidationUtils;
import org.springframework.validation.Validator;
public class ContentValidator implements Validator{
@Override
public boolean supports(Class<?> clazz) {
return false;
}
@Override
public void validate(Object target, Errors errors) {
ContentDto dto = (ContentDto)target;
// 전달 객체의 멤버 변수를 꺼내어 보지 않고 null이거나 비어 있는지 점검
ValidationUtils.rejectIfEmptyOrWhitespace(errors, "writer", "writer is empty.");
ValidationUtils.rejectIfEmptyOrWhitespace(errors, "content", "content is empty.");
// 전달된 특정 멤버변수의 글자수 점검
String sWriter = dto.getWriter();
if (sWriter.length() < 3) {
errors.rejectValue("writer", "writer is too short.");
}
}
}
package com.ecl.g07;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.validation.BindingResult;
import org.springframework.web.bind.annotation.ModelAttribute;
import org.springframework.web.bind.annotation.RequestMapping;
@Controller
public class ValidController {
@RequestMapping("/")
public String main() {
return "startPage";
}
@RequestMapping("/create")
public String create(
@ModelAttribute("dto") ContentDto contentdto, Model model,
BindingResult result) {
ContentValidator valid = new ContentValidator();
valid.validate(contentdto, result);
if (result.hasErrors()) {
if(result.getFieldError("writer")!=null)
model.addAttribute("message","writer를 써주세요");
else
model.addAttribute("message","content를 써주세요");
return "startPage";
}else {
return "DonePage";
}
}
}

Validation 이용하기

package com.ecl.g08;
import javax.validation.constraints.NotEmpty;
import javax.validation.constraints.NotNull;
import javax.validation.constraints.Size;
import lombok.Data;
@Data
public class ContentDto {
@NotNull(message="Writer is Null")
@NotEmpty(message="Writer is Empty")
@Size(min=4, max=20, message="writer min 4, max 20.")
private String writer;
@NotNull (message="Content is Null")
@NotEmpty (message="Content is Empty")
private String content;
private String name;
}
package com.ecl.g08;
import javax.validation.Valid;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.validation.BindingResult;
import org.springframework.web.bind.annotation.ModelAttribute;
import org.springframework.web.bind.annotation.RequestMapping;
@Controller
public class ValidController {
@RequestMapping("/")
public String root() throws Exception{
return "startPage";
}
@RequestMapping("/create")
public String create(
@ModelAttribute("dto") @Valid ContentDto contentDto ,
BindingResult result , Model model) {
String page = "DonePage";
if(result.hasErrors()) { // 어느 멤버변수인지 모르지만, 에러내용이 존재한다면
page = "startPage";
if( result.getFieldError("writer") != null) {
//model.addAttribute("message", "writer 가 비어 있거나 3글자 미만이면 안됩니다.");
model.addAttribute("message", result.getFieldError("writer").getDefaultMessage());
} else if(result.getFieldError("content") != null) {
model.addAttribute("message", result.getFieldError("content").getDefaultMessage());
}
} else {
}
return page;
}
}