SlideShare a Scribd company logo
효율적인 데이터 검증
Bean Validation 1.1
KSUG Spring-camp ( 2016 )
( JSR-349 )
조원태
: Yello Travel Labs - 우리펜션 개발팀
: qhanf27@gmail.com
“Bean Validation”
목차
 Bean Validation 소개
 일반적인 데이터 검증
 Bean Validation을 사용한 데이터 검증
 기본적으로 제공하는 Annotation 종류
 구현체에서 제공하는 Annotation 종류
 Pattren Annotation 을 사용한 전화번호 검증
 사용자 정의 Annotation – Custom Contstraint
 Annotation 속성 – groups
 Annotation 속성 – messages
 Annotation 속성 – payload
 Annotation 사용 시 유의사항
 Bean Validation 요약
 추가적으로 다루고싶은 내용
 참고자료
Bean Validation 소개
Bean Validation : 소개
Bean Validation 이란?
 데이터를 검증하기 위한 Java 표준 기술
 검증규칙은 Annotation 으로 사용
 데이터의 검증은 Runtime 시에 이루어짐
Client
Presentation
Layer
Business
Layer
Data Access
Layer
Database
Java
Domain
Model
Bean Validation : 소개
Bean Validation Release
Bean Validation 1.0
JSR-303
2009. XX. XX.
Bean Validation 1.1
JSR-349
2013. XX. XX.
Bean Validation : 소개
Bean Validation 구현체
Bean Validation 1.1
Specification
Hibernate
Validator
Apache
Bean Validation
Application
Java EE
6 and 7
Version 5.0 이상 Version 1.1 이상
구현체
API
우리가 흔히 사용하는 일반적인
데이터 검증
Bean Validation : 일반적인 데이터 검증
public class User {
private String name;
private Int age;
... (getter / setter)
... (toString)
}
일반적인 User Model
Bean Validation : 일반적인 데이터 검증
public void validate(User user) throws Exception {
if(user.getName() == null) {
throw new IllegalArgumentException("이름은 필수 정보입니다.");
}
if(user.getAge() <= 19) {
throw new IllegalArgumentException("나이는 19살 이상이어야 합니다.");
}
}
일반적인 Validate
Bean Validation 을 사용한 데이터 검증
Bean Validation : Bean Validation을 사용한 데이터 검증
public class User {
@NotNull
private String name;
@Min(value = 19)
private Int age;
... (getter / setter)
... (toString)
}
Annotation 선언된 User Model
Annotation 으로 해당
필드에 검증규칙을 선언
Bean Validation : Bean Validation을 사용한 데이터 검증
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
Set<ConstraintViolation<User>> constraintviolation = validator.validate(user);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage());
}
}
}
}
Bean Validaiton Validate
Bean Validation : Bean Validation을 사용한 데이터 검증
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
Set<ConstraintViolation<User>> constraintviolation = validator.validate(user);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage());
}
}
}
}
Bean Validaiton Validate
Bean Validation : Bean Validation을 사용한 데이터 검증
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
Set<ConstraintViolation<User>> constraintviolation = validator.validate(user);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage());
}
}
}
}
Bean Validaiton Validate
Bean Validation : Bean Validation을 사용한 데이터 검증
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
Set<ConstraintViolation<User>> constraintviolation = validator.validate(user);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage());
}
}
}
}
Bean Validaiton Validate
Bean Validation : Bean Validation을 사용한 데이터 검증
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
Set<ConstraintViolation<User>> constraintviolation = validator.validate(user);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage());
}
}
}
}
Bean Validaiton Validate
Bean Validation : Bean Validation을 사용한 데이터 검증
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
Set<ConstraintViolation<User>> constraintviolation = validator.validate(user);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage());
}
}
}
}
Bean Validaiton Validate
Bean Validation : Bean Validation을 사용한 데이터 검증
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
Set<ConstraintViolation<User>> constraintviolation = validator.validate(user);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage());
}
}
}
}
Bean Validaiton Validate
Bean Validation : Bean Validation을 사용한 데이터 검증
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
Set<ConstraintViolation<User>> constraintviolation = validator.validate(user);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage());
}
}
}
}
Bean Validaiton Validate
Bean Validation : Bean Validation을 사용한 데이터 검증
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
Set<ConstraintViolation<User>> constraintviolation = validator.validate(user);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage());
}
}
}
}
Bean Validaiton Validate
검증 실패
name : 반드시 값이 있어야 합니다.
age : 반드시 19보다 같거나 커야 합니다.
Bean Validtaion 에서
기본적으로 제공하는 Annotaion
Annotation 통과 조건 Annotation 통과 조건
@AssertFalse 거짓인가? @AssertTrue 참인가?
@Max 지정 값 이하인가? @Min 지정 값 이상인가?
@DecimalMax 지정 값 이하 실수인가? @DecimalMin 지정 값 이상 실수인가?
@NotNull Null이 아닌가? @Null Null인가?
@Digits 정수, 소수자리 수 이내인가? @Pattern 정규식을 만족하는가?
@Future 미래 날짜인가? @Size 지정 크기를 만족하는가?
@Past 과거 날짜인가? @Valid 객체의 확인 조건을 만족하는가?
Bean Validation : 기본적으로 제공하는 Annotaion 종류
Constraint Annotation
Annotation 통과 조건 Annotation 통과 조건
@AssertFalse 거짓인가? @AssertTrue 참인가?
@Max 지정 값 이하인가? @Min 지정 값 이상인가?
@DecimalMax 지정 값 이하 실수인가? @DecimalMin 지정 값 이상 실수인가?
@NotNull Null이 아닌가? @Null Null인가?
@Digits 정수, 소수자리 수 이내인가? @Pattern 정규식을 만족하는가?
@Future 미래 날짜인가? @Size 지정 크기를 만족하는가?
@Past 과거 날짜인가? @Valid 객체의 확인 조건을 만족하는가?
Bean Validation : 기본적으로 제공하는 Anntation 종류
Constraint Annotation
필드의 값이 Null이 아님을 확인하는 검증규칙
필드의 최소값을 지정할 수 있는 검증규칙
Hibernate 에서
확장하여 제공하는 Annotaion
Annotation 통과 조건 Annotation 통과 조건
@NotEmpty Empty값이 아닌가? @Email Email 형식인가?
@URL URL 형식인가? @Length 문자열 길이 min 과 max 사이인가?
@Range 숫자 범위 min 과 max 사이인가?
Bean Validation : 구현체에서 제공하는 Annotation 종류
Hibernate Constraint Annotation
Pattern Annotation 사용한
전화번호 검증
Bean Validation : Pattren Annotation을 사용한 전화번호 검증
public class User {
@Pattern(regexp="^[0-9]d{2}-(d{3}|d{4})-d{4}$")
private String phone;
... (getter / setter)
... (toString)
}
Pattern Annotation 선언된 User Model
전화번호 형식의
정규식을 만족하는가?
Bean Validation : Pattren Annotation을 사용한 전화번호 검증
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
user.setPhone(“000-0000-0000”);
Set<ConstraintViolation<User>> constraintviolation = validator.validate(user);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage());
}
}
}
}
Bean Validaiton Validate : Success
전화번호 형식
Bean Validation : Pattren Annotation을 사용한 전화번호 검증
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
user.setPhone(“000-0000-0000”);
Set<ConstraintViolation<User>> constraintviolation = validator.validate(user);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage());
}
}
}
}
Bean Validaiton Validate : Success
Bean Validation : Pattren Annotation을 사용한 전화번호 검증
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
user.setPhone(“000-0000-0000”);
Set<ConstraintViolation<User>> constraintviolation = validator.validate(user);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage());
}
}
}
}
Bean Validaiton Validate : Success
전화번호 형식
Bean Validation : Pattren Annotation을 사용한 전화번호 검증
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
user.setPhone(“000-0000-0000”);
Set<ConstraintViolation<User>> constraintviolation = validator.validate(user);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage());
}
}
}
}
Bean Validaiton Validate : Success
Bean Validation : Pattren Annotation을 사용한 전화번호 검증
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
user.setPhone(“000-0000-0000”);
Set<ConstraintViolation<User>> constraintviolation = validator.validate(user);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage());
}
}
}
}
Bean Validaiton Validate : Success
Bean Validation : Pattren Annotation을 사용한 전화번호 검증
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
user.setPhone(“000-0000-0000”);
Set<ConstraintViolation<User>> constraintviolation = validator.validate(user);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage());
}
}
}
}
Bean Validaiton Validate : Success
Bean Validation : Pattren Annotation을 사용한 전화번호 검증
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
user.setPhone(“000-0000-0000”);
Set<ConstraintViolation<User>> constraintviolation = validator.validate(user);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage());
}
}
}
}
Bean Validaiton Validate : Success
검증 성공
Bean Validation : Pattren Annotation을 사용한 전화번호 검증
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
user.setPhone(“00000000000”);
Set<ConstraintViolation<User>> constraintviolation = validator.validate(user);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage());
}
}
}
}
Bean Validaiton Validate : Fail
일반숫자 형식
Bean Validation : Pattren Annotation을 사용한 전화번호 검증
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
user.setPhone(“00000000000”);
Set<ConstraintViolation<User>> constraintviolation = validator.validate(user);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage());
}
}
}
}
Bean Validaiton Validate : Fail
Bean Validation : Pattren Annotation을 사용한 전화번호 검증
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
user.setPhone(“00000000000”);
Set<ConstraintViolation<User>> constraintviolation = validator.validate(user);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage());
}
}
}
}
Bean Validaiton Validate : Fail
일반숫자 형식
Bean Validation : Pattren Annotation을 사용한 전화번호 검증
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
user.setPhone(“00000000000”);
Set<ConstraintViolation<User>> constraintviolation = validator.validate(user);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage());
}
}
}
}
Bean Validaiton Validate : Fail
Bean Validation : Pattren Annotation을 사용한 전화번호 검증
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
user.setPhone(“00000000000”);
Set<ConstraintViolation<User>> constraintviolation = validator.validate(user);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage());
}
}
}
}
Bean Validaiton Validate : Fail
Bean Validation : Pattren Annotation을 사용한 전화번호 검증
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
user.setPhone(“00000000000”);
Set<ConstraintViolation<User>> constraintviolation = validator.validate(user);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage());
}
}
}
}
Bean Validaiton Validate : Fail
Bean Validation : Pattren Annotation을 사용한 전화번호 검증
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
user.setPhone(“00000000000”);
Set<ConstraintViolation<User>> constraintviolation = validator.validate(user);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage());
}
}
}
}
Bean Validaiton Validate : Fail
검증 실패
phone : 정규 표현식 [0-9]d{2}-(d{3}|d{4})-d{4}$ 패턴과 일치해야 합니다.
사용자가 직접 정의하여 사용하는
Annotation
Bean Validation : 사용자 정의 Annotation – Custom Contstraint
Custom Constraints 란?
 사용되는 경우
: 기본적으로 제공되는 Anntation 만으로 검증이 어려울 경우
: Annotation 직접 정의하여 사용
 Custom Constraints 필수 구성
: Custom Annotation
: Custom Validator
Bean Validation : 사용자 정의 Annotation – Custom Contstraint
@Target({ElementType.METHOD, ElementType.FIELD})
@Retention(RetentionPolicy.RUNTIME)
@Constraint(validatedBy = PhoneValidator.class)
@Size(min = 12, max = 13)
public @interface PhoneAnnotation {
String message() default “{phone.message}”;
Class<?>[] groups() default {};
Class<? extends Payload>[] payload() default {};
}
Custom Annotation 정의
Bean Validation : 사용자 정의 Annotation – Custom Contstraint
@Target({ElementType.METHOD, ElementType.FIELD})
@Retention(RetentionPolicy.RUNTIME)
@Constraint(validatedBy = PhoneValidator.class)
@Size(min = 12, max = 13)
public @interface PhoneAnnotation {
String message() default “{Phone.message}”;
Class<?>[] groups() default {};
Class<? extends Payload>[] payload() default {};
}
Custom Annotation 정의 METHOD, FIELD 에
검증규칙을 선언 가능
Bean Validation : 사용자 정의 Annotation – Custom Contstraint
@Target({ElementType.METHOD, ElementType.FIELD})
@Retention(RetentionPolicy.RUNTIME)
@Constraint(validatedBy = PhoneValidator.class)
@Size(min = 12, max = 13)
public @interface PhoneAnnotation {
String message() default “{Phone.message}”;
Class<?>[] groups() default {};
Class<? extends Payload>[] payload() default {};
}
Custom Annotation 정의
데이터 검증은
RUMTIME 시 적용
Bean Validation : 사용자 정의 Annotation – Custom Contstraint
@Target({ElementType.METHOD, ElementType.FIELD})
@Retention(RetentionPolicy.RUNTIME)
@Constraint(validatedBy = PhoneValidator.class)
@Size(min = 12, max = 13)
public @interface PhoneAnnotation {
String message() default “{Phone.message}”;
Class<?>[] groups() default {};
Class<? extends Payload>[] payload() default {};
}
Custom Annotation 정의
정의된 Validator에 의해
데이터 검증
Bean Validation : 사용자 정의 Annotation – Custom Contstraint
@Target({ElementType.METHOD, ElementType.FIELD})
@Retention(RetentionPolicy.RUNTIME)
@Constraint(validatedBy = PhoneValidator.class)
@Size(min = 12, max = 13)
public @interface PhoneAnnotation {
String message() default “{Phone.message}”;
Class<?>[] groups() default {};
Class<? extends Payload>[] payload() default {};
}
Custom Annotation 정의
Custom Annotation 에서
다른 Anootation 을 선언 가능
Bean Validation : 사용자 정의 Annotation – Custom Contstraint
@Target({ElementType.METHOD, ElementType.FIELD})
@Retention(RetentionPolicy.RUNTIME)
@Constraint(validatedBy = PhoneValidator.class)
@Size(min = 12, max = 13)
public @interface PhoneAnnotation {
String message() default “{Phone.message}”;
Class<?>[] groups() default {};
Class<? extends Payload>[] payload() default {};
}
Custom Annotation 정의
Custom Annotation 이
기본적으로 갖고 있는 속성
Bean Validation : 사용자 정의 Annotation – Custom Contstraint
public class PhoneValidator implements ConstraintValidator<PhoneAnnotaion, String> {
private java.util.regex.Pattern pattern
= java.util.regex.Pattern.compile(“^[0-9]d{2}-(d{3}|d{4})-d{4}$”);
public void initialize(PhoneAnnotation annotaton) {
}
public boolean isValid(String value. ConstraintValidatorContext context) {
if(value == null || value.length() == 0) {
return true;
}
Matcher m = pattern.matcher(value);
return m.matches();
}
}
Custom Validator 정의
Bean Validation : 사용자 정의 Annotation – Custom Contstraint
public class PhoneValidator implements ConstraintValidator<PhoneAnnotaion, String> {
private java.util.regex.Pattern pattern
= java.util.regex.Pattern.compile(“^[0-9]d{2}
public void initialize(PhoneAnnotation annotaton) {
}
public boolean isValid(String value. ConstraintValidatorContext context) {
if(value == null || value.length() == 0) {
return true;
}
Matcher m = pattern.matcher(value);
return m.matches();
}
}
Custom Validator 정의
Custom Validator 에서
필수적으로 Implements 하는
Interface
Bean Validation : 사용자 정의 Annotation – Custom Contstraint
public class PhoneValidator implements ConstraintValidator<PhoneAnnotaion, String> {
private java.util.regex.Pattern pattern
= java.util.regex.Pattern.compile(“^[0-9]d{2}-(d{3}|d{4})-d{4}$”);
public void initialize(PhoneAnnotation annotaton) {
}
public boolean isValid(String value. ConstraintValidatorContext context) {
if(value == null || value.length() == 0) {
return true;
}
Matcher m = pattern.matcher(value);
return m.matches();
}
}
Custom Validator 정의
검증규칙으로 사용될
정규식 패턴
Bean Validation : 사용자 정의 Annotation – Custom Contstraint
public class PhoneValidator implements ConstraintValidator<PhoneAnnotaion, String> {
private java.util.regex.Pattern pattern
= java.util.regex.Pattern.compile(“^[0-9]d{2}-(d{3}|d{4})-d{4}$”);
public void initialize(PhoneAnnotation annotaton) {
}
public boolean isValid(String value. ConstraintValidatorContext context) {
if(value == null || value.length() == 0) {
return true;
}
Matcher m = pattern.matcher(value);
return m.matches();
}
}
Custom Validator 정의
실제로 데이터 검증이
이루어지는 로직
Bean Validation : 사용자 정의 Annotation – Custom Contstraint
Custom Constraints 선언된 Model
… …
public class User {
@PhoneAnnotaion
private String phone;
... (getter / setter)
... (toString)
}
public class Address {
@PhoneAnnotaion
private String phone;
... (getter / setter)
... (toString)
}
여러 Model 에서의
Custom Constraints 사용
그룹정보 속성을 사용한 동일한 필드에서
서로 다른 데이터 검증
Bean Validation : Annotation 속성- groups
groups 무엇인가?
 검증규칙에 대한 그룹 정보를 정의
 그룹 정보에 따라 동일한 필드 값에 대해서도 서로 다른 데이터 검증
아이디
KSUG 등록
∨가입
비밀번호
이름
전화번호
public class User {
private String id;
private String password;
private String name;
private String phone;
}
아이디
KSUG 수정
∨가입
비밀번호
이름
전화번호
Bean Validation : Annotation 속성- groups
import javax.validation.groups.Default;
public interface Insert extends Default {
};
public interface Update extends Default {
};
groups 정의
사용자의 등록 단계를 체크할
Insert group 정의
사용자의 수정 단계를 체크할
Update group 정의
Bean Validation : Annotation 속성- groups
public class User {
@NotNull(groups = Insert.class)
private String name;
@Min(value = 19, groups = {Insert.class, Update.class})
private Int age;
... (getter / setter)
... (toString)
}
groups 정보가 추가로 정의된 User Model
groups 정보
Insert.class 정의
groups 정보
Insert.class, Update.class 정의
Bean Validation : Annotation 속성- groups
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
Set<ConstraintViolation<User>> constraintviolation
= validator.validate(user, Insert.class);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage());
}
}
}
}
Bean Validaiton Validate : Insert
데이터 검증 수행 시
Insert.class 그룹정보 바인드
Bean Validation : Annotation 속성- groups
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
Set<ConstraintViolation<User>> constraintviolation
= validator.validate(user, Insert.class);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage());
}
}
}
}
Bean Validaiton Validate : Insert
Bean Validation : Annotation 속성- groups
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
Set<ConstraintViolation<User>> constraintviolation
= validator.validate(user, Insert.class);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage());
}
}
}
}
Bean Validaiton Validate : Insert
Bean Validation : Annotation 속성- groups
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
Set<ConstraintViolation<User>> constraintviolation
= validator.validate(user, Insert.class);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage());
}
}
}
}
Bean Validaiton Validate : Insert
데이터 검증 수행 시
Insert.class 그룹정보 바인드
Bean Validation : Annotation 속성- groups
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
Set<ConstraintViolation<User>> constraintviolation
= validator.validate(user, Insert.class);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage());
}
}
}
}
Bean Validaiton Validate : Insert
Bean Validation : Annotation 속성- groups
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
Set<ConstraintViolation<User>> constraintviolation
= validator.validate(user, Insert.class);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage());
}
}
}
}
Bean Validaiton Validate : Insert
Bean Validation : Annotation 속성- groups
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
Set<ConstraintViolation<User>> constraintviolation
= validator.validate(user, Insert.class);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage());
}
}
}
}
Bean Validaiton Validate : Insert
검증 실패
name : 반드시 값이 있어야 합니다.
age : 반드시 19보다 같거나 커야 합니다.
Bean Validation : Annotation 속성- groups
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
Set<ConstraintViolation<User>> constraintviolation
= validator.validate(user, Update.class);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage());
}
}
}
}
Bean Validaiton Validate : Update
데이터 검증 수행 시
Update.class 그룹정보 바인드
Bean Validation : Annotation 속성- groups
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
Set<ConstraintViolation<User>> constraintviolation
= validator.validate(user, Update.class);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage());
}
}
}
}
Bean Validaiton Validate : Update
Bean Validation : Annotation 속성- groups
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
Set<ConstraintViolation<User>> constraintviolation
= validator.validate(user, Update.class);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage());
}
}
}
}
Bean Validaiton Validate : Update
Bean Validation : Annotation 속성- groups
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
Set<ConstraintViolation<User>> constraintviolation
= validator.validate(user, Update.class);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage());
}
}
}
}
Bean Validaiton Validate : Update
데이터 검증 수행 시
Update.class 그룹정보 바인드
Bean Validation : Annotation 속성- groups
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
Set<ConstraintViolation<User>> constraintviolation
= validator.validate(user, Update.class);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage());
}
}
}
}
Bean Validaiton Validate : Update
Bean Validation : Annotation 속성- groups
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
Set<ConstraintViolation<User>> constraintviolation
= validator.validate(user, Update.class);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage());
}
}
}
}
Bean Validaiton Validate : Update
Bean Validation : Annotation 속성- groups
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
Set<ConstraintViolation<User>> constraintviolation
= validator.validate(user, Update.class);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage());
}
}
}
}
Bean Validaiton Validate : Update
검증 실패
age : 반드시 19보다 같거나 커야 합니다.
메시지 속성을 사용한 메시지 표현
Bean Validation : Annotation 속성- message
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
user.setPhone(“00000000000”);
Set<ConstraintViolation<User>> constraintviolation = validator.validate(user);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage());
}
}
}
}
Pattren Annotaion을 사용한 검증에서의 message
검증 실패
phone : 정규 표현식 [0-9]d{2}-(d{3}|d{4})-d{4}$" 패턴과 일치해야 합니다.
불친절한 메시지 표현
Bean Validation : Annotation 속성- message
message 무엇인가?
 Annotation 에러 메시지를 정의하여 표현 가능
 Annotation 기본적인 메시지로 표현이 힘들 경우 사용
Bean Validation : Annotation 속성- message
public class User {
@Pattern(regexp = "^[0-9]d{2}-(d{3}|d{4})-d{4}$“
, message = “전화번호 형식이 아닙니다.”)
private String phone;
... (getter / setter)
... (toString)
}
message 정보가 추가로 정의된 User Model
검증규칙에
message 속성을 정의
Bean Validation : Annotation 속성- message
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
user.setPhone(“00000000000”);
Set<ConstraintViolation<User>> constraintviolation = validator.validate(user);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage());
}
}
}
}
message 속성을 사용한 검증에서의 message
검증 실패
phone : 전화번호 형식이 아닙니다.
친절한 메시지 표현
properties을 이용한 메시지 관리
Bean Validation : messageInterpolator
Properties 사용한 message 관리
user.id.null = id를 입력하세요.
user.name.null = 이름을 입력하세요.
user.password.null = 비밀번호를 입력하세요.
user.phone.null = 전화번호를 입력하세요.
.
.
.
아이디
KSUG 등록
∨가입
비밀번호
이름
전화번호
message.properties 파일
동일한 Annotation에서
서로 다른 심각도 정보를 표시
Bean Validation : Annotation 속성- payload
payload 무엇인가?
 검증규칙에 대한 더 자세한 정보 정의
 데이터 검증 에러가 발생하였을 경우 정의된 정보로 심각도 확인
 Payload 정의된 정보에 따라 처리가 가능
Bean Validation : Annotation 속성- payload
import javax.validation.Payload;
public class Severity {
public static interface Warning extends Payload {
};
public static interface Error extends Payload {
};
}
payload 정보 정의
경고를 표현할
Warning payload 정의
에러를 표현할
Error payload 정의
Bean Validation : Annotation 속성- payload
public class User {
@NotNull(payload = Serverity.Error.class)
private String name;
@NotNull (payload = Serverity.Warning.class)
private Int age;
... (getter / setter)
... (toString)
}
payload 정보가 추가로 정의된 User Model
payload 정보
Error.class 정의
payload 정보
Warning.class 정의
Bean Validation : Annotation 속성- payload
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
Set<ConstraintViolation<User>> constraintviolation = validator.validate(user);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath()
+ ” : “ + cv.getConstraintDescriptor().getPayload());
}
}
}
}
Bean Validaiton Validate
Bean Validation : Annotation 속성- payload
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
Set<ConstraintViolation<User>> constraintviolation = validator.validate(user);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath()
+ ” : “ + cv.getConstraintDescriptor().getPayload());
}
}
}
}
Bean Validaiton Validate
Bean Validation : Annotation 속성- payload
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
Set<ConstraintViolation<User>> constraintviolation = validator.validate(user);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath()
+ ” : “ + cv.getConstraintDescriptor().getPayload());
}
}
}
}
Bean Validaiton Validate
Bean Validation : Annotation 속성- payload
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
Set<ConstraintViolation<User>> constraintviolation = validator.validate(user);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath()
+ ” : “ + cv.getConstraintDescriptor().getPayload());
}
}
}
}
Bean Validaiton Validate
Bean Validation : Annotation 속성- payload
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
Set<ConstraintViolation<User>> constraintviolation = validator.validate(user);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath()
+ ” : “ + cv.getConstraintDescriptor().getPayload());
}
}
}
}
Bean Validaiton Validate
Bean Validation : Annotation 속성- payload
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
Set<ConstraintViolation<User>> constraintviolation = validator.validate(user);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath()
+ ” : “ + cv.getConstraintDescriptor().getPayload());
}
}
}
}
Bean Validaiton Validate
Bean Validation : Annotation 속성- payload
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
Set<ConstraintViolation<User>> constraintviolation = validator.validate(user);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath()
+ ” : “ + cv.getConstraintDescriptor().getPayload());
}
}
}
}
Bean Validaiton Validate
Bean Validation : Annotation 속성- payload
public class Main {
public static void main(String[] arg) throws Exception {
ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory();
Validator validator = validatorfactory.getValidator();
User user = new User();
Set<ConstraintViolation<User>> constraintviolation = validator.validate(user);
if(constraintviolation.size() == 0) {
System.out.println(“검증 성공”);
} else {
System.out.println(“검증 실패”);
for(ConstraintViolation<User> cv : constraintviolation) {
System.out.println(cv.getPropertyPath()
+ ” : “ + cv.getConstraintDescriptor().getPayload());
}
}
}
}
Bean Validaiton Validate
검증 실패
name : [interface com.example.beanvalidation.payload.PayloadInterface$Error]
age : [interface com.example.beanvalidation.payload.PayloadInterface$Warning]
같은 Null 값에 대해서도 payload 속성에
따라 서로 다른 심각도 정보 표현 가능
Annotation 사용시 유의사항
Bean Validation : 유의사항
Constraint Annotation 의 사용시 유의사항
 검증규칙의 모순을 구분하지 않고 검증을 진행
@Min(1) @DecimalMin(“0.2”)
int value;
@Min(3) @Max(2)
int value;
 검증규칙의 데이터 유형이 다를 경우 Exception 발생
@Past
int value;
@Pattern(regexp=“ .+@.+.[a-z]+”)
int value;
value 는 1이상이면서 0.2이상의 실수인가?
Bean Validation : 유의사항
Constraint Annotation 의 사용시 유의사항
 검증규칙의 모순을 구분하지 않고 검증을 진행
@Min(1) @DecimalMin(“0.2”)
int value;
@Min(3) @Max(2)
int value;
 검증규칙의 데이터 유형이 다를 경우 Exception 발생
@Past
int value;
@Pattern(regexp=“ .+@.+.[a-z]+”)
int value;
value 는 3이상이면서 2이하인가?
Bean Validation : 유의사항
Constraint Annotation 의 사용시 유의사항
 검증규칙의 모순을 구분하지 않고 검증을 진행
@Min(1) @DecimalMin(“0.2”)
int value;
@Min(3) @Max(2)
int value;
 검증규칙의 데이터 유형이 다를 경우 Exception 발생
@Past
int value;
@Pattern(regexp=“ .+@.+.[a-z]+”)
int value;
value 는 과거 날짜인가?
Bean Validation : 유의사항
Constraint Annotation 의 사용시 유의사항
 검증규칙의 모순을 구분하지 않고 검증을 진행
@Min(1) @DecimalMin(“0.2”)
int value;
@Min(3) @Max(2)
int value;
 검증규칙의 데이터 유형이 다를 경우 Exception 발생
@Past
int value;
@Pattern(regexp=“ .+@.+.[a-z]+”)
int value;
value 정규식을 만족하는가?
Bean Validation : 요약
Bean Validation 요약
 필드에 사용된 Annotation으로 런타임 시에 데이터 검증
 필요에 따라 사용자가 직접 Annotation을 정의 가능
 Annotation 속성
: groups - 동일한 Model에서의 서로 다른 검증
: message - 사용자 정의 메시지 표현
: payload - 데이터 검증 에러 시 상세 정보 표현
 사용시 유의사항
: 검증규칙의 모순을 구분하지 않고 검증을 진행
: 검증규칙의 데이터 유형이 다를 경우 Exception 발생
Bean Validation : 추가적으로 다루고싶은 내용
추가적으로 다루고싶은 내용
 Class에서의 데이터 검증
 EL표현식을 사용한 message 표현
 Spring MVC에서의 Bean Validation 사용
Bean Validation : 참고자료
참고자료
 JSR-349 Specification
: https://jcp.org/en/jsr/detail?id=349
 Java Bean Validation API - 발표자료
: http://www.slideshare.net/lguerin/cours-javabean-validationv11
 SpringMVC Bean Validation 1.1 (JSR-349) – 블로그
: http://jinnianshilongnian.iteye.com/blog/1495594
 Spring3.1 Bean Validation – 블로그
: http://jinnianshilongnian.iteye.com/blog/1990081
 Spring 3의 JSR 303(Bean Validation) 지원 – 발표자료
: http://www.slideshare.net/kingori/spring-3-jsr-303
고맙습니다
KSUG Spring-camp ( 2016 )

More Related Content

What's hot

C++ 프로젝트에 단위 테스트 도입하기
C++ 프로젝트에 단위 테스트 도입하기C++ 프로젝트에 단위 테스트 도입하기
C++ 프로젝트에 단위 테스트 도입하기
OnGameServer
 
C++ 프로젝트에 단위 테스트 도입하기
C++ 프로젝트에 단위 테스트 도입하기C++ 프로젝트에 단위 테스트 도입하기
C++ 프로젝트에 단위 테스트 도입하기
Heo Seungwook
 

What's hot (20)

우아하게 준비하는 테스트와 리팩토링 - PyCon Korea 2018
우아하게 준비하는 테스트와 리팩토링 - PyCon Korea 2018우아하게 준비하는 테스트와 리팩토링 - PyCon Korea 2018
우아하게 준비하는 테스트와 리팩토링 - PyCon Korea 2018
 
[D2 campus seminar]개발자가 꼭 알아야 할 보안이야기
[D2 campus seminar]개발자가 꼭 알아야 할 보안이야기[D2 campus seminar]개발자가 꼭 알아야 할 보안이야기
[D2 campus seminar]개발자가 꼭 알아야 할 보안이야기
 
JUnit 지원 라이브러리 소개
JUnit 지원 라이브러리 소개JUnit 지원 라이브러리 소개
JUnit 지원 라이브러리 소개
 
TDD with JUnit 2
TDD with JUnit 2TDD with JUnit 2
TDD with JUnit 2
 
Event source 학습 내용 공유
Event source 학습 내용 공유Event source 학습 내용 공유
Event source 학습 내용 공유
 
구글테스트
구글테스트구글테스트
구글테스트
 
Okjsp 13주년 발표자료: 생존 프로그래밍 Test
Okjsp 13주년 발표자료: 생존 프로그래밍 TestOkjsp 13주년 발표자료: 생존 프로그래밍 Test
Okjsp 13주년 발표자료: 생존 프로그래밍 Test
 
KGC2010 - 낡은 코드에 단위테스트 넣기
KGC2010 - 낡은 코드에 단위테스트 넣기KGC2010 - 낡은 코드에 단위테스트 넣기
KGC2010 - 낡은 코드에 단위테스트 넣기
 
C++ 프로젝트에 단위 테스트 도입하기
C++ 프로젝트에 단위 테스트 도입하기C++ 프로젝트에 단위 테스트 도입하기
C++ 프로젝트에 단위 테스트 도입하기
 
Spring 교육 자료
Spring 교육 자료Spring 교육 자료
Spring 교육 자료
 
Postman과 Newman을 이용한 RestAPI 테스트 자동화 가이드
Postman과 Newman을 이용한 RestAPI 테스트 자동화 가이드 Postman과 Newman을 이용한 RestAPI 테스트 자동화 가이드
Postman과 Newman을 이용한 RestAPI 테스트 자동화 가이드
 
사용자 스토리 대상 테스트 설계 사례(테스트기본교육 3장 3절)
사용자 스토리 대상 테스트 설계 사례(테스트기본교육 3장 3절)사용자 스토리 대상 테스트 설계 사례(테스트기본교육 3장 3절)
사용자 스토리 대상 테스트 설계 사례(테스트기본교육 3장 3절)
 
katalon studio 툴을 이용한 GUI 테스트 자동화 가이드
katalon studio 툴을 이용한 GUI 테스트 자동화 가이드katalon studio 툴을 이용한 GUI 테스트 자동화 가이드
katalon studio 툴을 이용한 GUI 테스트 자동화 가이드
 
2007년 제8회 JCO 컨퍼런스 POJO 프로그래밍 발표 자료
2007년 제8회 JCO 컨퍼런스 POJO 프로그래밍 발표 자료2007년 제8회 JCO 컨퍼런스 POJO 프로그래밍 발표 자료
2007년 제8회 JCO 컨퍼런스 POJO 프로그래밍 발표 자료
 
TDD.JUnit.조금더.알기
TDD.JUnit.조금더.알기TDD.JUnit.조금더.알기
TDD.JUnit.조금더.알기
 
테스트수행사례 W통합보안솔루션
테스트수행사례 W통합보안솔루션테스트수행사례 W통합보안솔루션
테스트수행사례 W통합보안솔루션
 
C++ 프로젝트에 단위 테스트 도입하기
C++ 프로젝트에 단위 테스트 도입하기C++ 프로젝트에 단위 테스트 도입하기
C++ 프로젝트에 단위 테스트 도입하기
 
AI 연구자를 위한 클린코드 - GDG DevFest Seoul 2019
AI 연구자를 위한 클린코드 - GDG DevFest Seoul 2019AI 연구자를 위한 클린코드 - GDG DevFest Seoul 2019
AI 연구자를 위한 클린코드 - GDG DevFest Seoul 2019
 
Jquery javascript_ed10
Jquery javascript_ed10Jquery javascript_ed10
Jquery javascript_ed10
 
SI 화면테스트(단위) 가이드
SI 화면테스트(단위) 가이드SI 화면테스트(단위) 가이드
SI 화면테스트(단위) 가이드
 

Similar to Bean validation 1.1

Spring camp 발표자료
Spring camp 발표자료Spring camp 발표자료
Spring camp 발표자료
수홍 이
 
[7/27 접근성세미나] 웹 접근성 진단 100% 자동화, 그 가능성을 말하다
[7/27 접근성세미나] 웹 접근성 진단 100% 자동화, 그 가능성을 말하다[7/27 접근성세미나] 웹 접근성 진단 100% 자동화, 그 가능성을 말하다
[7/27 접근성세미나] 웹 접근성 진단 100% 자동화, 그 가능성을 말하다
Nts Nuli
 
Visual studio team system with agile tech days 2010
Visual studio team system with agile tech days 2010Visual studio team system with agile tech days 2010
Visual studio team system with agile tech days 2010
준일 엄
 

Similar to Bean validation 1.1 (19)

Python Testing for Flask
Python Testing for FlaskPython Testing for Flask
Python Testing for Flask
 
Test and ci
Test and ciTest and ci
Test and ci
 
Spring camp 발표자료
Spring camp 발표자료Spring camp 발표자료
Spring camp 발표자료
 
Advanced Python Testing Techniques (Pycon KR 2019) [Korean Ver.]
Advanced Python Testing Techniques (Pycon KR 2019) [Korean Ver.]Advanced Python Testing Techniques (Pycon KR 2019) [Korean Ver.]
Advanced Python Testing Techniques (Pycon KR 2019) [Korean Ver.]
 
10장 결과 검증
10장 결과 검증10장 결과 검증
10장 결과 검증
 
AWS로 게임 런칭 준비하기 ::: 장준성, 채민관, AWS Game Master 온라인 시리즈 #4
AWS로 게임 런칭 준비하기 ::: 장준성, 채민관, AWS Game Master 온라인 시리즈 #4AWS로 게임 런칭 준비하기 ::: 장준성, 채민관, AWS Game Master 온라인 시리즈 #4
AWS로 게임 런칭 준비하기 ::: 장준성, 채민관, AWS Game Master 온라인 시리즈 #4
 
우리 제품의 검증 프로세스 소개 자료
우리 제품의 검증 프로세스 소개 자료 우리 제품의 검증 프로세스 소개 자료
우리 제품의 검증 프로세스 소개 자료
 
How to evaluate accessibility with automatic
How to evaluate accessibility with automaticHow to evaluate accessibility with automatic
How to evaluate accessibility with automatic
 
자바 웹 개발 시작하기 (7주차 : 국제화, 확인검증, 예외처리)
자바 웹 개발 시작하기 (7주차 : 국제화, 확인검증, 예외처리)자바 웹 개발 시작하기 (7주차 : 국제화, 확인검증, 예외처리)
자바 웹 개발 시작하기 (7주차 : 국제화, 확인검증, 예외처리)
 
테스터가 말하는 테스트코드 작성 팁과 사례
테스터가 말하는 테스트코드 작성 팁과 사례테스터가 말하는 테스트코드 작성 팁과 사례
테스터가 말하는 테스트코드 작성 팁과 사례
 
Cygnus unit test
Cygnus unit testCygnus unit test
Cygnus unit test
 
[7/27 접근성세미나] 웹 접근성 진단 100% 자동화, 그 가능성을 말하다
[7/27 접근성세미나] 웹 접근성 진단 100% 자동화, 그 가능성을 말하다[7/27 접근성세미나] 웹 접근성 진단 100% 자동화, 그 가능성을 말하다
[7/27 접근성세미나] 웹 접근성 진단 100% 자동화, 그 가능성을 말하다
 
테스트개선지원 사례 - 웹어플리케이션대상
테스트개선지원 사례 - 웹어플리케이션대상테스트개선지원 사례 - 웹어플리케이션대상
테스트개선지원 사례 - 웹어플리케이션대상
 
Python codelab3
Python codelab3Python codelab3
Python codelab3
 
AWS Step Functions을 통한 마이크로서비스 오케스트레이션 - 강세용:: AWS 현대적 애플리케이션 개발
AWS Step Functions을 통한 마이크로서비스 오케스트레이션 - 강세용:: AWS 현대적 애플리케이션 개발AWS Step Functions을 통한 마이크로서비스 오케스트레이션 - 강세용:: AWS 현대적 애플리케이션 개발
AWS Step Functions을 통한 마이크로서비스 오케스트레이션 - 강세용:: AWS 현대적 애플리케이션 개발
 
Xe3.0 frontend validator
Xe3.0 frontend validatorXe3.0 frontend validator
Xe3.0 frontend validator
 
Robot framework 을 이용한 기능 테스트 자동화
Robot framework 을 이용한 기능 테스트 자동화Robot framework 을 이용한 기능 테스트 자동화
Robot framework 을 이용한 기능 테스트 자동화
 
Visual studio team system with agile tech days 2010
Visual studio team system with agile tech days 2010Visual studio team system with agile tech days 2010
Visual studio team system with agile tech days 2010
 
Online service 계층별 성능 모니터링 방안
Online service 계층별 성능 모니터링 방안Online service 계층별 성능 모니터링 방안
Online service 계층별 성능 모니터링 방안
 

Recently uploaded

캡스톤-디자인-최종-발표-(대상혁) 24년도 졸업작품발표회 ppt.pptx
캡스톤-디자인-최종-발표-(대상혁) 24년도 졸업작품발표회 ppt.pptx캡스톤-디자인-최종-발표-(대상혁) 24년도 졸업작품발표회 ppt.pptx
캡스톤-디자인-최종-발표-(대상혁) 24년도 졸업작품발표회 ppt.pptx
cho9759
 
INU Graduation Powerpoint-Rabbit FootPrint
INU Graduation Powerpoint-Rabbit FootPrintINU Graduation Powerpoint-Rabbit FootPrint
INU Graduation Powerpoint-Rabbit FootPrint
ahghwo99
 

Recently uploaded (7)

캡스톤-디자인-최종-발표-(대상혁) 24년도 졸업작품발표회 ppt.pptx
캡스톤-디자인-최종-발표-(대상혁) 24년도 졸업작품발표회 ppt.pptx캡스톤-디자인-최종-발표-(대상혁) 24년도 졸업작품발표회 ppt.pptx
캡스톤-디자인-최종-발표-(대상혁) 24년도 졸업작품발표회 ppt.pptx
 
인천대학교 캡스톤디자인(2) Pencil me 프레젠테이션 발표자료 파일
인천대학교 캡스톤디자인(2) Pencil me 프레젠테이션 발표자료 파일인천대학교 캡스톤디자인(2) Pencil me 프레젠테이션 발표자료 파일
인천대학교 캡스톤디자인(2) Pencil me 프레젠테이션 발표자료 파일
 
(독서광) 대격변 AI 시대, 데이터로 사고하고 데이터로 리드하라
(독서광) 대격변 AI 시대,   데이터로 사고하고   데이터로 리드하라(독서광) 대격변 AI 시대,   데이터로 사고하고   데이터로 리드하라
(독서광) 대격변 AI 시대, 데이터로 사고하고 데이터로 리드하라
 
암호화 보안USB & 외장하드 중앙관리 솔루션 ‘DataLocker SafeConsole’_DATASHEET
암호화 보안USB & 외장하드 중앙관리 솔루션 ‘DataLocker SafeConsole’_DATASHEET암호화 보안USB & 외장하드 중앙관리 솔루션 ‘DataLocker SafeConsole’_DATASHEET
암호화 보안USB & 외장하드 중앙관리 솔루션 ‘DataLocker SafeConsole’_DATASHEET
 
INU Graduation Powerpoint-Rabbit FootPrint
INU Graduation Powerpoint-Rabbit FootPrintINU Graduation Powerpoint-Rabbit FootPrint
INU Graduation Powerpoint-Rabbit FootPrint
 
인천대학교 컴퓨터공학과 아틀란티스 졸업작품 commINUty PPT
인천대학교 컴퓨터공학과 아틀란티스 졸업작품 commINUty PPT인천대학교 컴퓨터공학과 아틀란티스 졸업작품 commINUty PPT
인천대학교 컴퓨터공학과 아틀란티스 졸업작품 commINUty PPT
 
2024년 5월 27일 개발자 이야기 - AWS 람다의 내부 동작 방식 외
2024년 5월 27일 개발자 이야기 - AWS 람다의 내부 동작 방식 외2024년 5월 27일 개발자 이야기 - AWS 람다의 내부 동작 방식 외
2024년 5월 27일 개발자 이야기 - AWS 람다의 내부 동작 방식 외
 

Bean validation 1.1

  • 1. 효율적인 데이터 검증 Bean Validation 1.1 KSUG Spring-camp ( 2016 ) ( JSR-349 )
  • 2. 조원태 : Yello Travel Labs - 우리펜션 개발팀 : qhanf27@gmail.com
  • 3. “Bean Validation” 목차  Bean Validation 소개  일반적인 데이터 검증  Bean Validation을 사용한 데이터 검증  기본적으로 제공하는 Annotation 종류  구현체에서 제공하는 Annotation 종류  Pattren Annotation 을 사용한 전화번호 검증  사용자 정의 Annotation – Custom Contstraint  Annotation 속성 – groups  Annotation 속성 – messages  Annotation 속성 – payload  Annotation 사용 시 유의사항  Bean Validation 요약  추가적으로 다루고싶은 내용  참고자료
  • 5. Bean Validation : 소개 Bean Validation 이란?  데이터를 검증하기 위한 Java 표준 기술  검증규칙은 Annotation 으로 사용  데이터의 검증은 Runtime 시에 이루어짐 Client Presentation Layer Business Layer Data Access Layer Database Java Domain Model
  • 6. Bean Validation : 소개 Bean Validation Release Bean Validation 1.0 JSR-303 2009. XX. XX. Bean Validation 1.1 JSR-349 2013. XX. XX.
  • 7. Bean Validation : 소개 Bean Validation 구현체 Bean Validation 1.1 Specification Hibernate Validator Apache Bean Validation Application Java EE 6 and 7 Version 5.0 이상 Version 1.1 이상 구현체 API
  • 8. 우리가 흔히 사용하는 일반적인 데이터 검증
  • 9. Bean Validation : 일반적인 데이터 검증 public class User { private String name; private Int age; ... (getter / setter) ... (toString) } 일반적인 User Model
  • 10. Bean Validation : 일반적인 데이터 검증 public void validate(User user) throws Exception { if(user.getName() == null) { throw new IllegalArgumentException("이름은 필수 정보입니다."); } if(user.getAge() <= 19) { throw new IllegalArgumentException("나이는 19살 이상이어야 합니다."); } } 일반적인 Validate
  • 11. Bean Validation 을 사용한 데이터 검증
  • 12. Bean Validation : Bean Validation을 사용한 데이터 검증 public class User { @NotNull private String name; @Min(value = 19) private Int age; ... (getter / setter) ... (toString) } Annotation 선언된 User Model Annotation 으로 해당 필드에 검증규칙을 선언
  • 13. Bean Validation : Bean Validation을 사용한 데이터 검증 public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage()); } } } } Bean Validaiton Validate
  • 14. Bean Validation : Bean Validation을 사용한 데이터 검증 public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage()); } } } } Bean Validaiton Validate
  • 15. Bean Validation : Bean Validation을 사용한 데이터 검증 public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage()); } } } } Bean Validaiton Validate
  • 16. Bean Validation : Bean Validation을 사용한 데이터 검증 public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage()); } } } } Bean Validaiton Validate
  • 17. Bean Validation : Bean Validation을 사용한 데이터 검증 public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage()); } } } } Bean Validaiton Validate
  • 18. Bean Validation : Bean Validation을 사용한 데이터 검증 public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage()); } } } } Bean Validaiton Validate
  • 19. Bean Validation : Bean Validation을 사용한 데이터 검증 public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage()); } } } } Bean Validaiton Validate
  • 20. Bean Validation : Bean Validation을 사용한 데이터 검증 public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage()); } } } } Bean Validaiton Validate
  • 21. Bean Validation : Bean Validation을 사용한 데이터 검증 public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage()); } } } } Bean Validaiton Validate 검증 실패 name : 반드시 값이 있어야 합니다. age : 반드시 19보다 같거나 커야 합니다.
  • 22. Bean Validtaion 에서 기본적으로 제공하는 Annotaion
  • 23. Annotation 통과 조건 Annotation 통과 조건 @AssertFalse 거짓인가? @AssertTrue 참인가? @Max 지정 값 이하인가? @Min 지정 값 이상인가? @DecimalMax 지정 값 이하 실수인가? @DecimalMin 지정 값 이상 실수인가? @NotNull Null이 아닌가? @Null Null인가? @Digits 정수, 소수자리 수 이내인가? @Pattern 정규식을 만족하는가? @Future 미래 날짜인가? @Size 지정 크기를 만족하는가? @Past 과거 날짜인가? @Valid 객체의 확인 조건을 만족하는가? Bean Validation : 기본적으로 제공하는 Annotaion 종류 Constraint Annotation
  • 24. Annotation 통과 조건 Annotation 통과 조건 @AssertFalse 거짓인가? @AssertTrue 참인가? @Max 지정 값 이하인가? @Min 지정 값 이상인가? @DecimalMax 지정 값 이하 실수인가? @DecimalMin 지정 값 이상 실수인가? @NotNull Null이 아닌가? @Null Null인가? @Digits 정수, 소수자리 수 이내인가? @Pattern 정규식을 만족하는가? @Future 미래 날짜인가? @Size 지정 크기를 만족하는가? @Past 과거 날짜인가? @Valid 객체의 확인 조건을 만족하는가? Bean Validation : 기본적으로 제공하는 Anntation 종류 Constraint Annotation 필드의 값이 Null이 아님을 확인하는 검증규칙 필드의 최소값을 지정할 수 있는 검증규칙
  • 26. Annotation 통과 조건 Annotation 통과 조건 @NotEmpty Empty값이 아닌가? @Email Email 형식인가? @URL URL 형식인가? @Length 문자열 길이 min 과 max 사이인가? @Range 숫자 범위 min 과 max 사이인가? Bean Validation : 구현체에서 제공하는 Annotation 종류 Hibernate Constraint Annotation
  • 28. Bean Validation : Pattren Annotation을 사용한 전화번호 검증 public class User { @Pattern(regexp="^[0-9]d{2}-(d{3}|d{4})-d{4}$") private String phone; ... (getter / setter) ... (toString) } Pattern Annotation 선언된 User Model 전화번호 형식의 정규식을 만족하는가?
  • 29. Bean Validation : Pattren Annotation을 사용한 전화번호 검증 public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); user.setPhone(“000-0000-0000”); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage()); } } } } Bean Validaiton Validate : Success 전화번호 형식
  • 30. Bean Validation : Pattren Annotation을 사용한 전화번호 검증 public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); user.setPhone(“000-0000-0000”); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage()); } } } } Bean Validaiton Validate : Success
  • 31. Bean Validation : Pattren Annotation을 사용한 전화번호 검증 public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); user.setPhone(“000-0000-0000”); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage()); } } } } Bean Validaiton Validate : Success 전화번호 형식
  • 32. Bean Validation : Pattren Annotation을 사용한 전화번호 검증 public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); user.setPhone(“000-0000-0000”); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage()); } } } } Bean Validaiton Validate : Success
  • 33. Bean Validation : Pattren Annotation을 사용한 전화번호 검증 public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); user.setPhone(“000-0000-0000”); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage()); } } } } Bean Validaiton Validate : Success
  • 34. Bean Validation : Pattren Annotation을 사용한 전화번호 검증 public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); user.setPhone(“000-0000-0000”); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage()); } } } } Bean Validaiton Validate : Success
  • 35. Bean Validation : Pattren Annotation을 사용한 전화번호 검증 public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); user.setPhone(“000-0000-0000”); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage()); } } } } Bean Validaiton Validate : Success 검증 성공
  • 36. Bean Validation : Pattren Annotation을 사용한 전화번호 검증 public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); user.setPhone(“00000000000”); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage()); } } } } Bean Validaiton Validate : Fail 일반숫자 형식
  • 37. Bean Validation : Pattren Annotation을 사용한 전화번호 검증 public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); user.setPhone(“00000000000”); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage()); } } } } Bean Validaiton Validate : Fail
  • 38. Bean Validation : Pattren Annotation을 사용한 전화번호 검증 public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); user.setPhone(“00000000000”); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage()); } } } } Bean Validaiton Validate : Fail 일반숫자 형식
  • 39. Bean Validation : Pattren Annotation을 사용한 전화번호 검증 public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); user.setPhone(“00000000000”); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage()); } } } } Bean Validaiton Validate : Fail
  • 40. Bean Validation : Pattren Annotation을 사용한 전화번호 검증 public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); user.setPhone(“00000000000”); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage()); } } } } Bean Validaiton Validate : Fail
  • 41. Bean Validation : Pattren Annotation을 사용한 전화번호 검증 public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); user.setPhone(“00000000000”); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage()); } } } } Bean Validaiton Validate : Fail
  • 42. Bean Validation : Pattren Annotation을 사용한 전화번호 검증 public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); user.setPhone(“00000000000”); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage()); } } } } Bean Validaiton Validate : Fail 검증 실패 phone : 정규 표현식 [0-9]d{2}-(d{3}|d{4})-d{4}$ 패턴과 일치해야 합니다.
  • 43. 사용자가 직접 정의하여 사용하는 Annotation
  • 44. Bean Validation : 사용자 정의 Annotation – Custom Contstraint Custom Constraints 란?  사용되는 경우 : 기본적으로 제공되는 Anntation 만으로 검증이 어려울 경우 : Annotation 직접 정의하여 사용  Custom Constraints 필수 구성 : Custom Annotation : Custom Validator
  • 45. Bean Validation : 사용자 정의 Annotation – Custom Contstraint @Target({ElementType.METHOD, ElementType.FIELD}) @Retention(RetentionPolicy.RUNTIME) @Constraint(validatedBy = PhoneValidator.class) @Size(min = 12, max = 13) public @interface PhoneAnnotation { String message() default “{phone.message}”; Class<?>[] groups() default {}; Class<? extends Payload>[] payload() default {}; } Custom Annotation 정의
  • 46. Bean Validation : 사용자 정의 Annotation – Custom Contstraint @Target({ElementType.METHOD, ElementType.FIELD}) @Retention(RetentionPolicy.RUNTIME) @Constraint(validatedBy = PhoneValidator.class) @Size(min = 12, max = 13) public @interface PhoneAnnotation { String message() default “{Phone.message}”; Class<?>[] groups() default {}; Class<? extends Payload>[] payload() default {}; } Custom Annotation 정의 METHOD, FIELD 에 검증규칙을 선언 가능
  • 47. Bean Validation : 사용자 정의 Annotation – Custom Contstraint @Target({ElementType.METHOD, ElementType.FIELD}) @Retention(RetentionPolicy.RUNTIME) @Constraint(validatedBy = PhoneValidator.class) @Size(min = 12, max = 13) public @interface PhoneAnnotation { String message() default “{Phone.message}”; Class<?>[] groups() default {}; Class<? extends Payload>[] payload() default {}; } Custom Annotation 정의 데이터 검증은 RUMTIME 시 적용
  • 48. Bean Validation : 사용자 정의 Annotation – Custom Contstraint @Target({ElementType.METHOD, ElementType.FIELD}) @Retention(RetentionPolicy.RUNTIME) @Constraint(validatedBy = PhoneValidator.class) @Size(min = 12, max = 13) public @interface PhoneAnnotation { String message() default “{Phone.message}”; Class<?>[] groups() default {}; Class<? extends Payload>[] payload() default {}; } Custom Annotation 정의 정의된 Validator에 의해 데이터 검증
  • 49. Bean Validation : 사용자 정의 Annotation – Custom Contstraint @Target({ElementType.METHOD, ElementType.FIELD}) @Retention(RetentionPolicy.RUNTIME) @Constraint(validatedBy = PhoneValidator.class) @Size(min = 12, max = 13) public @interface PhoneAnnotation { String message() default “{Phone.message}”; Class<?>[] groups() default {}; Class<? extends Payload>[] payload() default {}; } Custom Annotation 정의 Custom Annotation 에서 다른 Anootation 을 선언 가능
  • 50. Bean Validation : 사용자 정의 Annotation – Custom Contstraint @Target({ElementType.METHOD, ElementType.FIELD}) @Retention(RetentionPolicy.RUNTIME) @Constraint(validatedBy = PhoneValidator.class) @Size(min = 12, max = 13) public @interface PhoneAnnotation { String message() default “{Phone.message}”; Class<?>[] groups() default {}; Class<? extends Payload>[] payload() default {}; } Custom Annotation 정의 Custom Annotation 이 기본적으로 갖고 있는 속성
  • 51. Bean Validation : 사용자 정의 Annotation – Custom Contstraint public class PhoneValidator implements ConstraintValidator<PhoneAnnotaion, String> { private java.util.regex.Pattern pattern = java.util.regex.Pattern.compile(“^[0-9]d{2}-(d{3}|d{4})-d{4}$”); public void initialize(PhoneAnnotation annotaton) { } public boolean isValid(String value. ConstraintValidatorContext context) { if(value == null || value.length() == 0) { return true; } Matcher m = pattern.matcher(value); return m.matches(); } } Custom Validator 정의
  • 52. Bean Validation : 사용자 정의 Annotation – Custom Contstraint public class PhoneValidator implements ConstraintValidator<PhoneAnnotaion, String> { private java.util.regex.Pattern pattern = java.util.regex.Pattern.compile(“^[0-9]d{2} public void initialize(PhoneAnnotation annotaton) { } public boolean isValid(String value. ConstraintValidatorContext context) { if(value == null || value.length() == 0) { return true; } Matcher m = pattern.matcher(value); return m.matches(); } } Custom Validator 정의 Custom Validator 에서 필수적으로 Implements 하는 Interface
  • 53. Bean Validation : 사용자 정의 Annotation – Custom Contstraint public class PhoneValidator implements ConstraintValidator<PhoneAnnotaion, String> { private java.util.regex.Pattern pattern = java.util.regex.Pattern.compile(“^[0-9]d{2}-(d{3}|d{4})-d{4}$”); public void initialize(PhoneAnnotation annotaton) { } public boolean isValid(String value. ConstraintValidatorContext context) { if(value == null || value.length() == 0) { return true; } Matcher m = pattern.matcher(value); return m.matches(); } } Custom Validator 정의 검증규칙으로 사용될 정규식 패턴
  • 54. Bean Validation : 사용자 정의 Annotation – Custom Contstraint public class PhoneValidator implements ConstraintValidator<PhoneAnnotaion, String> { private java.util.regex.Pattern pattern = java.util.regex.Pattern.compile(“^[0-9]d{2}-(d{3}|d{4})-d{4}$”); public void initialize(PhoneAnnotation annotaton) { } public boolean isValid(String value. ConstraintValidatorContext context) { if(value == null || value.length() == 0) { return true; } Matcher m = pattern.matcher(value); return m.matches(); } } Custom Validator 정의 실제로 데이터 검증이 이루어지는 로직
  • 55. Bean Validation : 사용자 정의 Annotation – Custom Contstraint Custom Constraints 선언된 Model … … public class User { @PhoneAnnotaion private String phone; ... (getter / setter) ... (toString) } public class Address { @PhoneAnnotaion private String phone; ... (getter / setter) ... (toString) } 여러 Model 에서의 Custom Constraints 사용
  • 56. 그룹정보 속성을 사용한 동일한 필드에서 서로 다른 데이터 검증
  • 57. Bean Validation : Annotation 속성- groups groups 무엇인가?  검증규칙에 대한 그룹 정보를 정의  그룹 정보에 따라 동일한 필드 값에 대해서도 서로 다른 데이터 검증 아이디 KSUG 등록 ∨가입 비밀번호 이름 전화번호 public class User { private String id; private String password; private String name; private String phone; } 아이디 KSUG 수정 ∨가입 비밀번호 이름 전화번호
  • 58. Bean Validation : Annotation 속성- groups import javax.validation.groups.Default; public interface Insert extends Default { }; public interface Update extends Default { }; groups 정의 사용자의 등록 단계를 체크할 Insert group 정의 사용자의 수정 단계를 체크할 Update group 정의
  • 59. Bean Validation : Annotation 속성- groups public class User { @NotNull(groups = Insert.class) private String name; @Min(value = 19, groups = {Insert.class, Update.class}) private Int age; ... (getter / setter) ... (toString) } groups 정보가 추가로 정의된 User Model groups 정보 Insert.class 정의 groups 정보 Insert.class, Update.class 정의
  • 60. Bean Validation : Annotation 속성- groups public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user, Insert.class); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage()); } } } } Bean Validaiton Validate : Insert 데이터 검증 수행 시 Insert.class 그룹정보 바인드
  • 61. Bean Validation : Annotation 속성- groups public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user, Insert.class); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage()); } } } } Bean Validaiton Validate : Insert
  • 62. Bean Validation : Annotation 속성- groups public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user, Insert.class); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage()); } } } } Bean Validaiton Validate : Insert
  • 63. Bean Validation : Annotation 속성- groups public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user, Insert.class); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage()); } } } } Bean Validaiton Validate : Insert 데이터 검증 수행 시 Insert.class 그룹정보 바인드
  • 64. Bean Validation : Annotation 속성- groups public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user, Insert.class); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage()); } } } } Bean Validaiton Validate : Insert
  • 65. Bean Validation : Annotation 속성- groups public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user, Insert.class); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage()); } } } } Bean Validaiton Validate : Insert
  • 66. Bean Validation : Annotation 속성- groups public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user, Insert.class); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage()); } } } } Bean Validaiton Validate : Insert 검증 실패 name : 반드시 값이 있어야 합니다. age : 반드시 19보다 같거나 커야 합니다.
  • 67. Bean Validation : Annotation 속성- groups public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user, Update.class); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage()); } } } } Bean Validaiton Validate : Update 데이터 검증 수행 시 Update.class 그룹정보 바인드
  • 68. Bean Validation : Annotation 속성- groups public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user, Update.class); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage()); } } } } Bean Validaiton Validate : Update
  • 69. Bean Validation : Annotation 속성- groups public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user, Update.class); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage()); } } } } Bean Validaiton Validate : Update
  • 70. Bean Validation : Annotation 속성- groups public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user, Update.class); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage()); } } } } Bean Validaiton Validate : Update 데이터 검증 수행 시 Update.class 그룹정보 바인드
  • 71. Bean Validation : Annotation 속성- groups public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user, Update.class); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage()); } } } } Bean Validaiton Validate : Update
  • 72. Bean Validation : Annotation 속성- groups public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user, Update.class); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage()); } } } } Bean Validaiton Validate : Update
  • 73. Bean Validation : Annotation 속성- groups public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user, Update.class); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage()); } } } } Bean Validaiton Validate : Update 검증 실패 age : 반드시 19보다 같거나 커야 합니다.
  • 74. 메시지 속성을 사용한 메시지 표현
  • 75. Bean Validation : Annotation 속성- message public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); user.setPhone(“00000000000”); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage()); } } } } Pattren Annotaion을 사용한 검증에서의 message 검증 실패 phone : 정규 표현식 [0-9]d{2}-(d{3}|d{4})-d{4}$" 패턴과 일치해야 합니다. 불친절한 메시지 표현
  • 76. Bean Validation : Annotation 속성- message message 무엇인가?  Annotation 에러 메시지를 정의하여 표현 가능  Annotation 기본적인 메시지로 표현이 힘들 경우 사용
  • 77. Bean Validation : Annotation 속성- message public class User { @Pattern(regexp = "^[0-9]d{2}-(d{3}|d{4})-d{4}$“ , message = “전화번호 형식이 아닙니다.”) private String phone; ... (getter / setter) ... (toString) } message 정보가 추가로 정의된 User Model 검증규칙에 message 속성을 정의
  • 78. Bean Validation : Annotation 속성- message public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); user.setPhone(“00000000000”); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getMessage()); } } } } message 속성을 사용한 검증에서의 message 검증 실패 phone : 전화번호 형식이 아닙니다. 친절한 메시지 표현
  • 80. Bean Validation : messageInterpolator Properties 사용한 message 관리 user.id.null = id를 입력하세요. user.name.null = 이름을 입력하세요. user.password.null = 비밀번호를 입력하세요. user.phone.null = 전화번호를 입력하세요. . . . 아이디 KSUG 등록 ∨가입 비밀번호 이름 전화번호 message.properties 파일
  • 81. 동일한 Annotation에서 서로 다른 심각도 정보를 표시
  • 82. Bean Validation : Annotation 속성- payload payload 무엇인가?  검증규칙에 대한 더 자세한 정보 정의  데이터 검증 에러가 발생하였을 경우 정의된 정보로 심각도 확인  Payload 정의된 정보에 따라 처리가 가능
  • 83. Bean Validation : Annotation 속성- payload import javax.validation.Payload; public class Severity { public static interface Warning extends Payload { }; public static interface Error extends Payload { }; } payload 정보 정의 경고를 표현할 Warning payload 정의 에러를 표현할 Error payload 정의
  • 84. Bean Validation : Annotation 속성- payload public class User { @NotNull(payload = Serverity.Error.class) private String name; @NotNull (payload = Serverity.Warning.class) private Int age; ... (getter / setter) ... (toString) } payload 정보가 추가로 정의된 User Model payload 정보 Error.class 정의 payload 정보 Warning.class 정의
  • 85. Bean Validation : Annotation 속성- payload public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getConstraintDescriptor().getPayload()); } } } } Bean Validaiton Validate
  • 86. Bean Validation : Annotation 속성- payload public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getConstraintDescriptor().getPayload()); } } } } Bean Validaiton Validate
  • 87. Bean Validation : Annotation 속성- payload public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getConstraintDescriptor().getPayload()); } } } } Bean Validaiton Validate
  • 88. Bean Validation : Annotation 속성- payload public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getConstraintDescriptor().getPayload()); } } } } Bean Validaiton Validate
  • 89. Bean Validation : Annotation 속성- payload public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getConstraintDescriptor().getPayload()); } } } } Bean Validaiton Validate
  • 90. Bean Validation : Annotation 속성- payload public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getConstraintDescriptor().getPayload()); } } } } Bean Validaiton Validate
  • 91. Bean Validation : Annotation 속성- payload public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getConstraintDescriptor().getPayload()); } } } } Bean Validaiton Validate
  • 92. Bean Validation : Annotation 속성- payload public class Main { public static void main(String[] arg) throws Exception { ValidatorFactory validatorfactory = Validation.buildDefaultValidatorFactory(); Validator validator = validatorfactory.getValidator(); User user = new User(); Set<ConstraintViolation<User>> constraintviolation = validator.validate(user); if(constraintviolation.size() == 0) { System.out.println(“검증 성공”); } else { System.out.println(“검증 실패”); for(ConstraintViolation<User> cv : constraintviolation) { System.out.println(cv.getPropertyPath() + ” : “ + cv.getConstraintDescriptor().getPayload()); } } } } Bean Validaiton Validate 검증 실패 name : [interface com.example.beanvalidation.payload.PayloadInterface$Error] age : [interface com.example.beanvalidation.payload.PayloadInterface$Warning] 같은 Null 값에 대해서도 payload 속성에 따라 서로 다른 심각도 정보 표현 가능
  • 94. Bean Validation : 유의사항 Constraint Annotation 의 사용시 유의사항  검증규칙의 모순을 구분하지 않고 검증을 진행 @Min(1) @DecimalMin(“0.2”) int value; @Min(3) @Max(2) int value;  검증규칙의 데이터 유형이 다를 경우 Exception 발생 @Past int value; @Pattern(regexp=“ .+@.+.[a-z]+”) int value; value 는 1이상이면서 0.2이상의 실수인가?
  • 95. Bean Validation : 유의사항 Constraint Annotation 의 사용시 유의사항  검증규칙의 모순을 구분하지 않고 검증을 진행 @Min(1) @DecimalMin(“0.2”) int value; @Min(3) @Max(2) int value;  검증규칙의 데이터 유형이 다를 경우 Exception 발생 @Past int value; @Pattern(regexp=“ .+@.+.[a-z]+”) int value; value 는 3이상이면서 2이하인가?
  • 96. Bean Validation : 유의사항 Constraint Annotation 의 사용시 유의사항  검증규칙의 모순을 구분하지 않고 검증을 진행 @Min(1) @DecimalMin(“0.2”) int value; @Min(3) @Max(2) int value;  검증규칙의 데이터 유형이 다를 경우 Exception 발생 @Past int value; @Pattern(regexp=“ .+@.+.[a-z]+”) int value; value 는 과거 날짜인가?
  • 97. Bean Validation : 유의사항 Constraint Annotation 의 사용시 유의사항  검증규칙의 모순을 구분하지 않고 검증을 진행 @Min(1) @DecimalMin(“0.2”) int value; @Min(3) @Max(2) int value;  검증규칙의 데이터 유형이 다를 경우 Exception 발생 @Past int value; @Pattern(regexp=“ .+@.+.[a-z]+”) int value; value 정규식을 만족하는가?
  • 98. Bean Validation : 요약 Bean Validation 요약  필드에 사용된 Annotation으로 런타임 시에 데이터 검증  필요에 따라 사용자가 직접 Annotation을 정의 가능  Annotation 속성 : groups - 동일한 Model에서의 서로 다른 검증 : message - 사용자 정의 메시지 표현 : payload - 데이터 검증 에러 시 상세 정보 표현  사용시 유의사항 : 검증규칙의 모순을 구분하지 않고 검증을 진행 : 검증규칙의 데이터 유형이 다를 경우 Exception 발생
  • 99. Bean Validation : 추가적으로 다루고싶은 내용 추가적으로 다루고싶은 내용  Class에서의 데이터 검증  EL표현식을 사용한 message 표현  Spring MVC에서의 Bean Validation 사용
  • 100. Bean Validation : 참고자료 참고자료  JSR-349 Specification : https://jcp.org/en/jsr/detail?id=349  Java Bean Validation API - 발표자료 : http://www.slideshare.net/lguerin/cours-javabean-validationv11  SpringMVC Bean Validation 1.1 (JSR-349) – 블로그 : http://jinnianshilongnian.iteye.com/blog/1495594  Spring3.1 Bean Validation – 블로그 : http://jinnianshilongnian.iteye.com/blog/1990081  Spring 3의 JSR 303(Bean Validation) 지원 – 발표자료 : http://www.slideshare.net/kingori/spring-3-jsr-303