From a703fcadc162c5667e50348c300d7eddc9d26a2b Mon Sep 17 00:00:00 2001 From: ZhouXY108 Date: Fri, 15 Mar 2024 09:09:38 +0800 Subject: [PATCH] =?UTF-8?q?1.=20=E9=87=8D=E6=9E=84=E4=BB=A3=E7=A0=81?= =?UTF-8?q?=EF=BC=9B2.=20=E6=94=AF=E6=8C=81=E5=AF=B9=20POJO=20=E7=9A=84?= =?UTF-8?q?=E6=A0=A1=E9=AA=8C?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../validator/BasePropertyValidator.java | 51 +++++++++++ .../plusone/validator/EntryValidator.java | 20 +++++ .../plusone/validator/MapValidator.java | 48 +--------- .../plusone/validator/PredicateTools.java | 90 ------------------- .../plusone/validator/PropertyValidator.java | 17 ++++ .../{ => map}/MapValidatorTests.java | 39 ++++---- 6 files changed, 115 insertions(+), 150 deletions(-) create mode 100644 src/main/java/xyz/zhouxy/plusone/validator/BasePropertyValidator.java create mode 100644 src/main/java/xyz/zhouxy/plusone/validator/EntryValidator.java delete mode 100644 src/main/java/xyz/zhouxy/plusone/validator/PredicateTools.java create mode 100644 src/main/java/xyz/zhouxy/plusone/validator/PropertyValidator.java rename src/test/java/xyz/zhouxy/plusone/validator/{ => map}/MapValidatorTests.java (53%) diff --git a/src/main/java/xyz/zhouxy/plusone/validator/BasePropertyValidator.java b/src/main/java/xyz/zhouxy/plusone/validator/BasePropertyValidator.java new file mode 100644 index 0000000..e6b85bf --- /dev/null +++ b/src/main/java/xyz/zhouxy/plusone/validator/BasePropertyValidator.java @@ -0,0 +1,51 @@ +package xyz.zhouxy.plusone.validator; + +import java.util.LinkedList; +import java.util.List; +import java.util.function.Consumer; +import java.util.function.Function; +import java.util.function.Predicate; +import java.util.function.Supplier; + +public abstract class BasePropertyValidator> { + + private final Function getter; + + protected BasePropertyValidator(Function getter) { + this.getter = getter; + } + + private final List> consumers = new LinkedList<>(); + + public final TValidator withRules(Predicate rule) { + return withRules(rule, v -> new IllegalArgumentException()); + } + + public final TValidator withRules( + Predicate rule, String errorMsg) { + return withRules(rule, v -> new IllegalArgumentException(errorMsg)); + } + + public final TValidator withRules( + Predicate rule, Supplier e) { + return withRules(rule, v -> e.get()); + } + + public final TValidator withRules( + Predicate rule, Function e) { + this.consumers.add(v -> { + if (!rule.test(v)) { + throw e.apply(v); + } + }); + return thisObject(); + } + + public final void validate(T dto) { + for (Consumer consumer : consumers) { + consumer.accept(getter.apply(dto)); + } + } + + protected abstract TValidator thisObject(); +} diff --git a/src/main/java/xyz/zhouxy/plusone/validator/EntryValidator.java b/src/main/java/xyz/zhouxy/plusone/validator/EntryValidator.java new file mode 100644 index 0000000..e636574 --- /dev/null +++ b/src/main/java/xyz/zhouxy/plusone/validator/EntryValidator.java @@ -0,0 +1,20 @@ +package xyz.zhouxy.plusone.validator; + +import java.util.Map; + +public class EntryValidator + extends BasePropertyValidator, V, EntryValidator> { + + public EntryValidator(K key) { + super(m -> { + @SuppressWarnings("unchecked") + V v = (V) m.get(key); + return v; + }); + } + + @Override + protected EntryValidator thisObject() { + return this; + } +} diff --git a/src/main/java/xyz/zhouxy/plusone/validator/MapValidator.java b/src/main/java/xyz/zhouxy/plusone/validator/MapValidator.java index bc7f769..ead5388 100644 --- a/src/main/java/xyz/zhouxy/plusone/validator/MapValidator.java +++ b/src/main/java/xyz/zhouxy/plusone/validator/MapValidator.java @@ -51,12 +51,12 @@ public abstract class MapValidator { } @SuppressWarnings("unused") - protected final PropertyValidator checkProperty(K key, Class clazz) { + protected final EntryValidator checkProperty(K key, Class clazz) { return checkProperty(key); } - protected final PropertyValidator checkProperty(K key) { - PropertyValidator validator = new PropertyValidator<>(key); + protected final EntryValidator checkProperty(K key) { + EntryValidator validator = new EntryValidator<>(key); this.consumers.add(validator::validate); return validator; } @@ -81,45 +81,3 @@ public abstract class MapValidator { }); } } - -class PropertyValidator { - - private final K key; - - public PropertyValidator(K key) { - this.key = key; - } - - private final List> consumers = new LinkedList<>(); - - public final PropertyValidator withRules(Predicate rule) { - return withRules(rule, v -> new IllegalArgumentException(key.toString())); - } - - public final PropertyValidator withRules(Predicate rule, String errorMsg) { - return withRules(rule, v -> new IllegalArgumentException(errorMsg)); - } - - public final PropertyValidator withRules(Predicate rule, - Supplier e) { - return withRules(rule, v -> e.get()); - } - - public final PropertyValidator withRules(Predicate rule, - Function e) { - this.consumers.add(v -> { - if (!rule.test(v)) { - throw e.apply(v); - } - }); - return this; - } - - public final void validate(Map map) { - for (Consumer consumer : consumers) { - @SuppressWarnings("unchecked") - V v = (V) map.get(this.key); - consumer.accept(v); - } - } -} diff --git a/src/main/java/xyz/zhouxy/plusone/validator/PredicateTools.java b/src/main/java/xyz/zhouxy/plusone/validator/PredicateTools.java deleted file mode 100644 index b99e8cb..0000000 --- a/src/main/java/xyz/zhouxy/plusone/validator/PredicateTools.java +++ /dev/null @@ -1,90 +0,0 @@ -package xyz.zhouxy.plusone.validator; - -import java.util.Collection; -import java.util.function.Predicate; -import java.util.regex.Pattern; - -public class PredicateTools { - - private PredicateTools() { - throw new IllegalStateException("Utility class"); - } - - public static Predicate asPredicate(Predicate predicate) { - return predicate; - } - - public static boolean notNull(T obj) { - return obj != null; - } - - public static Predicate notNull() { - return PredicateTools::notNull; - } - - public static int length(CharSequence cs) { - return cs == null ? 0 : cs.length(); - } - - public static boolean isNotBlank(CharSequence cs) { - return !isBlank(cs); - } - - public static Predicate isNotBlank() { - return PredicateTools::isNotBlank; - } - - public static boolean isBlank(CharSequence cs) { - final int strLen = length(cs); - if (strLen == 0) { - return true; - } - for (int i = 0; i < strLen; i++) { - if (!Character.isWhitespace(cs.charAt(i))) { - return false; - } - } - return true; - } - - public static Predicate isBlank() { - return PredicateTools::isBlank; - } - - public static Predicate matches(Pattern pattern) { - return str -> pattern.matcher(str).matches(); - } - - public static Predicate matchesAll(Pattern... patterns) { - return str -> { - for (Pattern pattern : patterns) { - if (!pattern.matcher(str).matches()) { - return false; - } - } - return true; - }; - } - - public static Predicate matchesOne(Pattern... patterns) { - return str -> { - for (Pattern pattern : patterns) { - if (pattern.matcher(str).matches()) { - return true; - } - } - return false; - }; - } - - public static Predicate> forAllItems(Predicate predicate) { - return c -> { - for (T t : c) { - if (!predicate.test(t)) { - return false; - } - } - return true; - }; - } -} diff --git a/src/main/java/xyz/zhouxy/plusone/validator/PropertyValidator.java b/src/main/java/xyz/zhouxy/plusone/validator/PropertyValidator.java new file mode 100644 index 0000000..16ac92b --- /dev/null +++ b/src/main/java/xyz/zhouxy/plusone/validator/PropertyValidator.java @@ -0,0 +1,17 @@ +package xyz.zhouxy.plusone.validator; + +import java.util.function.Function; + +public class PropertyValidator + extends BasePropertyValidator> { + + protected PropertyValidator(Function getter) { + super(getter); + } + + @Override + protected PropertyValidator thisObject() { + return this; + } + +} diff --git a/src/test/java/xyz/zhouxy/plusone/validator/MapValidatorTests.java b/src/test/java/xyz/zhouxy/plusone/validator/map/MapValidatorTests.java similarity index 53% rename from src/test/java/xyz/zhouxy/plusone/validator/MapValidatorTests.java rename to src/test/java/xyz/zhouxy/plusone/validator/map/MapValidatorTests.java index 2efc21a..cd51e09 100644 --- a/src/test/java/xyz/zhouxy/plusone/validator/MapValidatorTests.java +++ b/src/test/java/xyz/zhouxy/plusone/validator/map/MapValidatorTests.java @@ -1,4 +1,4 @@ -package xyz.zhouxy.plusone.validator; +package xyz.zhouxy.plusone.validator.map; import static org.junit.jupiter.api.Assertions.*; @@ -7,11 +7,16 @@ import java.util.Collection; import java.util.HashMap; import java.util.Map; import java.util.Objects; +import java.util.regex.Pattern; import org.apache.commons.lang3.StringUtils; import org.junit.jupiter.api.Test; +import xyz.zhouxy.plusone.commons.collection.CollectionTools; import xyz.zhouxy.plusone.commons.constant.PatternConsts; +import xyz.zhouxy.plusone.commons.function.PredicateTools; +import xyz.zhouxy.plusone.commons.util.RegexUtil; +import xyz.zhouxy.plusone.validator.MapValidator; class MapValidatorTests { @@ -26,34 +31,38 @@ class MapValidatorTests { private static final MapValidator validator = new MapValidator( new String[] { USERNAME, ACCOUNT, PASSWORD, AGE, BOOLEAN, ROLE_LIST }) { { - checkProperty(USERNAME, String.class) - .withRules(StringUtils::isNotEmpty) - .withRules(PredicateTools.matches(PatternConsts.USERNAME), - username -> new IllegalArgumentException(String.format("用户名【%s】不符合规范", username))); + checkProperty(USERNAME, String.class).withRules( + PredicateTools.from(StringUtils::isNotBlank) + .and(username -> RegexUtil.matches(username, PatternConsts.USERNAME)), + username -> new IllegalArgumentException(String.format("用户名【%s】不符合规范", username))); - checkProperty(ACCOUNT, String.class) - .withRules(StringUtils::isNotEmpty) - .withRules(PredicateTools.matchesOne(PatternConsts.EMAIL, PatternConsts.MOBILE_PHONE), - "请输入正确的邮箱地址或手机号"); + checkProperty(ACCOUNT, String.class).withRules( + PredicateTools.from(StringUtils::isNotBlank) + .and(account -> RegexUtil.matchesOne(account, + new Pattern[] { PatternConsts.EMAIL, PatternConsts.MOBILE_PHONE })), + "请输入正确的邮箱地址或手机号"); checkProperty(PASSWORD, String.class) - .withRules(StringUtils::isNotEmpty) - .withRules(PredicateTools.matches(PatternConsts.PASSWORD), "密码不符合规范"); + .withRules(StringUtils::isNotEmpty, "密码不能为空") + .withRules(pwd -> RegexUtil.matches(pwd, PatternConsts.PASSWORD), "密码不符合规范"); + // 校验到多个属性,只能针对 map 本身进行校验 withRule(m -> Objects.equals(m.get(PASSWORD), m.get(PASSWORD2)), "两次输入的密码不一样!"); - checkProperty(AGE, Integer.class) + // 通过泛型方式调用方法,指定数据类型 + this.checkProperty(AGE) .withRules(Objects::nonNull) .withRules(age -> (18 <= age && 60 >= age)); checkProperty(BOOLEAN, Boolean.class) - .withRules(PredicateTools.notNull(), "Boolean property could not be null.") + .withRules(Objects::nonNull, "Boolean property could not be null.") .withRules(b -> b, "Boolean property must be true."); this.>checkProperty(ROLE_LIST) - .withRules(c -> c != null && !c.isEmpty(), "角色列表不能为空!") - .withRules(PredicateTools.forAllItems(Objects::nonNull), () -> new NullPointerException(ROLE_LIST)); + .withRules(CollectionTools::isNotEmpty, "角色列表不能为空!") + .withRules(l -> l.stream().allMatch(StringUtils::isNotBlank), + () -> new IllegalArgumentException(ROLE_LIST)); } };