All Downloads are FREE. Search and download functionalities are using the official Maven repository.

com.webcohesion.enunciate.util.BeanValidationUtils Maven / Gradle / Ivy

/**
 * Copyright © 2006-2016 Web Cohesion ([email protected])
 * 

* Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at *

* http://www.apache.org/licenses/LICENSE-2.0 *

* Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package com.webcohesion.enunciate.util; import com.webcohesion.enunciate.javac.decorations.Annotations; import com.webcohesion.enunciate.javac.decorations.DecoratedProcessingEnvironment; import com.webcohesion.enunciate.javac.decorations.element.DecoratedTypeElement; import com.webcohesion.enunciate.javac.decorations.type.DecoratedDeclaredType; import com.webcohesion.enunciate.javac.decorations.type.DecoratedTypeMirror; import com.webcohesion.enunciate.metadata.AllowedValues; import com.webcohesion.enunciate.metadata.ReadOnly; import javax.annotation.ParametersAreNonnullByDefault; import javax.lang.model.element.*; import javax.lang.model.type.DeclaredType; import javax.lang.model.type.PrimitiveType; import javax.lang.model.type.TypeMirror; import java.util.*; import java.util.stream.Collectors; /** * @author Ryan Heaton */ public class BeanValidationUtils { private static final Set OPTIONALS; private BeanValidationUtils() { } static { HashSet opts = new HashSet<>(); opts.add(Optional.class.getName()); opts.add(OptionalInt.class.getName()); opts.add(OptionalLong.class.getName()); opts.add(OptionalDouble.class.getName()); OPTIONALS = Collections.unmodifiableSet(opts); } public static boolean isNotNull(Element el) { return isNotNull(el, true); } private static boolean isNotNull(Element el, boolean recurse) { final TypeMirror asType = el.asType(); if (asType instanceof PrimitiveType) { return true; } if (asType instanceof DeclaredType && OPTIONALS.stream().anyMatch(p -> ((QualifiedNameable) ((DeclaredType) asType).asElement()).getQualifiedName().contentEquals(p))) { return false; } if (el.getAnnotation(javax.validation.constraints.NotNull.class) != null || el.getAnnotation(jakarta.validation.constraints.NotNull.class) != null || el.getAnnotation(javax.annotation.Nonnull.class) != null // no replacement in jakarta || el.getAnnotation(javax.validation.constraints.NotEmpty.class) != null || el.getAnnotation(jakarta.validation.constraints.NotEmpty.class) != null || el.getAnnotation(javax.validation.constraints.NotBlank.class) != null || el.getAnnotation(jakarta.validation.constraints.NotBlank.class) != null) { return true; } if (el.getAnnotation(javax.annotation.Nullable.class) != null) { return false; } List annotations = el.getAnnotationMirrors(); for (AnnotationMirror annotation : annotations) { DeclaredType annotationType = annotation.getAnnotationType(); if (annotationType != null) { Element annotationElement = annotationType.asElement(); try { if (annotationElement.getAnnotation(javax.validation.constraints.NotNull.class) != null || annotationElement.getAnnotation(jakarta.validation.constraints.NotNull.class) != null) { return true; } if (recurse && isNotNull(annotationElement, false)) { return true; } } catch (Exception e) { //See https://github.com/stoicflame/enunciate/issues/872; recursing sometimes encounters types not on the classpath. return false; } } } return notNullByDefault(el); } private static boolean notNullByDefault(Element el) { if (el == null) { return false; } if (el.getAnnotation(ParametersAreNonnullByDefault.class) != null) { return true; } return notNullByDefault(el.getEnclosingElement()); } public static boolean hasConstraints(Element el, boolean required) { if (required) { return true; } if (el.getAnnotation(ReadOnly.class) != null) { return true; } List annotations = el.getAnnotationMirrors(); for (AnnotationMirror annotation : annotations) { DeclaredType annotationType = annotation.getAnnotationType(); if (annotationType != null) { Element annotationElement = annotationType.asElement(); if (annotationElement != null) { Element pckg = annotationElement.getEnclosingElement(); if (pckg instanceof PackageElement) { String packageQualifiedName = ((PackageElement) pckg).getQualifiedName().toString(); boolean nameEqualsJavax = packageQualifiedName.equals("javax.validation.constraints"); boolean nameEqualsJakarta = packageQualifiedName.equals("jakarta.validation.constraints"); if (nameEqualsJakarta || nameEqualsJavax) { return true; } } } } } return false; } public static String describeConstraints(Element el, boolean required, boolean explicitlyNotRequired, String defaultValue, DecoratedProcessingEnvironment env) { javax.validation.constraints.Null mustBeNull = el.getAnnotation(javax.validation.constraints.Null.class); jakarta.validation.constraints.Null mustBeNull2 = el.getAnnotation(jakarta.validation.constraints.Null.class); if (mustBeNull != null || mustBeNull2 != null) { return "must be null"; } String type = describeTypeIfPrimitive(el); List constraints = new ArrayList(); required = required || (isNotNull(el) && defaultValue == null); if (required && !explicitlyNotRequired) { constraints.add("required" + type); } ReadOnly readOnly = el.getAnnotation(ReadOnly.class); if (readOnly != null) { constraints.add("read-only" + type); } javax.validation.constraints.AssertFalse mustBeFalse = el.getAnnotation(javax.validation.constraints.AssertFalse.class); jakarta.validation.constraints.AssertFalse mustBeFalse2 = el.getAnnotation(jakarta.validation.constraints.AssertFalse.class); if (mustBeFalse != null || mustBeFalse2 != null) { constraints.add("must be \"false\""); } javax.validation.constraints.AssertTrue mustBeTrue = el.getAnnotation(javax.validation.constraints.AssertTrue.class); jakarta.validation.constraints.AssertTrue mustBeTrue2 = el.getAnnotation(jakarta.validation.constraints.AssertTrue.class); if (mustBeTrue != null || mustBeTrue2 != null) { constraints.add("must be \"true\""); } javax.validation.constraints.DecimalMax decimalMax = el.getAnnotation(javax.validation.constraints.DecimalMax.class); jakarta.validation.constraints.DecimalMax decimalMax2 = el.getAnnotation(jakarta.validation.constraints.DecimalMax.class); if (decimalMax != null || decimalMax2 != null) { String value = decimalMax != null ? decimalMax.value() : decimalMax2.value(); boolean inclusive = decimalMax != null ? decimalMax.inclusive() : decimalMax2.inclusive(); constraints.add("max: " + value + (inclusive ? "" : " (exclusive)")); } javax.validation.constraints.DecimalMin decimalMin = el.getAnnotation(javax.validation.constraints.DecimalMin.class); jakarta.validation.constraints.DecimalMin decimalMin2 = el.getAnnotation(jakarta.validation.constraints.DecimalMin.class); if (decimalMin != null || decimalMin2 != null) { String value = decimalMin != null ? decimalMin.value() : decimalMin2.value(); boolean inclusive = decimalMin != null ? decimalMin.inclusive() : decimalMin2.inclusive(); constraints.add("min: " + value + (inclusive ? "" : " (exclusive)")); } javax.validation.constraints.Digits digits = el.getAnnotation(javax.validation.constraints.Digits.class); jakarta.validation.constraints.Digits digits2 = el.getAnnotation(jakarta.validation.constraints.Digits.class); if (digits != null || digits2 != null) { int integer = digits != null ? digits.integer() : digits2.integer(); int fraction = digits != null ? digits.fraction() : digits2.fraction(); constraints.add("max digits: " + integer + " (integer), " + fraction + " (fraction)"); } javax.validation.constraints.Future dateInFuture = el.getAnnotation(javax.validation.constraints.Future.class); jakarta.validation.constraints.Future dateInFuture2 = el.getAnnotation(jakarta.validation.constraints.Future.class); if (dateInFuture != null || dateInFuture2 != null) { constraints.add("future date"); } javax.validation.constraints.Max max = el.getAnnotation(javax.validation.constraints.Max.class); jakarta.validation.constraints.Max max2 = el.getAnnotation(jakarta.validation.constraints.Max.class); if (max != null || max2 != null) { constraints.add("max: " + (max != null ? max.value() : max2.value())); } javax.validation.constraints.Min min = el.getAnnotation(javax.validation.constraints.Min.class); jakarta.validation.constraints.Min min2 = el.getAnnotation(jakarta.validation.constraints.Min.class); if (min != null || min2 != null) { constraints.add("min: " + (min != null ? min.value() : min2.value())); } javax.validation.constraints.Past dateInPast = el.getAnnotation(javax.validation.constraints.Past.class); jakarta.validation.constraints.Past dateInPast2 = el.getAnnotation(jakarta.validation.constraints.Past.class); if (dateInPast != null || dateInPast2 != null) { constraints.add("past date"); } javax.validation.constraints.Pattern mustMatchPattern = el.getAnnotation(javax.validation.constraints.Pattern.class); jakarta.validation.constraints.Pattern mustMatchPattern2 = el.getAnnotation(jakarta.validation.constraints.Pattern.class); if (mustMatchPattern != null || mustMatchPattern2 != null) { constraints.add("regex: " + (mustMatchPattern != null ? mustMatchPattern.regexp() : mustMatchPattern2.regexp())); } AllowedValues allowedValues = el.getAnnotation(AllowedValues.class); if (allowedValues != null) { DecoratedTypeMirror enumMirror = Annotations.mirrorOf(allowedValues::value, env); String values = ((DecoratedTypeElement) ((DecoratedDeclaredType) enumMirror).asElement()).enumValues().stream().map(VariableElement::getSimpleName).collect(Collectors.joining(", ")); constraints.add("values: " + values); } javax.validation.constraints.Size size = el.getAnnotation(javax.validation.constraints.Size.class); jakarta.validation.constraints.Size size2 = el.getAnnotation(jakarta.validation.constraints.Size.class); if (size != null || size2 != null) { constraints.add("max size: " + (size != null ? size.max() : size2.max()) + ", min size: " + (size != null ? size.min() : size2.min())); } javax.validation.constraints.Email email = el.getAnnotation(javax.validation.constraints.Email.class); jakarta.validation.constraints.Email email2 = el.getAnnotation(jakarta.validation.constraints.Email.class); if (email != null || email2 != null) { constraints.add("e-mail"); } javax.validation.constraints.NotEmpty notEmpty = el.getAnnotation(javax.validation.constraints.NotEmpty.class); jakarta.validation.constraints.NotEmpty notEmpty2 = el.getAnnotation(jakarta.validation.constraints.NotEmpty.class); if (notEmpty != null || notEmpty2 != null) { constraints.add("not empty" + type); } javax.validation.constraints.NotBlank notBlank = el.getAnnotation(javax.validation.constraints.NotBlank.class); jakarta.validation.constraints.NotBlank notBlank2 = el.getAnnotation(jakarta.validation.constraints.NotBlank.class); if (notBlank != null || notBlank2 != null) { constraints.add("not blank" + type); } javax.validation.constraints.Positive positive = el.getAnnotation(javax.validation.constraints.Positive.class); jakarta.validation.constraints.Positive positive2 = el.getAnnotation(jakarta.validation.constraints.Positive.class); if (positive != null || positive2 != null) { constraints.add("positive" + type); } javax.validation.constraints.PositiveOrZero positiveOrZero = el.getAnnotation(javax.validation.constraints.PositiveOrZero.class); jakarta.validation.constraints.PositiveOrZero positiveOrZero2 = el.getAnnotation(jakarta.validation.constraints.PositiveOrZero.class); if (positiveOrZero != null || positiveOrZero2 != null) { constraints.add("positive or zero" + type); } javax.validation.constraints.Negative negative = el.getAnnotation(javax.validation.constraints.Negative.class); jakarta.validation.constraints.Negative negative2 = el.getAnnotation(jakarta.validation.constraints.Negative.class); if (negative != null || negative2 != null) { constraints.add("negative" + type); } javax.validation.constraints.NegativeOrZero negativeOrZero = el.getAnnotation(javax.validation.constraints.NegativeOrZero.class); jakarta.validation.constraints.NegativeOrZero negativeOrZero2 = el.getAnnotation(jakarta.validation.constraints.NegativeOrZero.class); if (negativeOrZero != null || negativeOrZero2 != null) { constraints.add("negative or zero" + type); } javax.validation.constraints.PastOrPresent pastOrPresent = el.getAnnotation(javax.validation.constraints.PastOrPresent.class); jakarta.validation.constraints.PastOrPresent pastOrPresent2 = el.getAnnotation(jakarta.validation.constraints.PastOrPresent.class); if (pastOrPresent != null || pastOrPresent2 != null) { constraints.add("past or present"); } javax.validation.constraints.FutureOrPresent futureOrPresent = el.getAnnotation(javax.validation.constraints.FutureOrPresent.class); jakarta.validation.constraints.FutureOrPresent futureOrPresent2 = el.getAnnotation(jakarta.validation.constraints.FutureOrPresent.class); if (futureOrPresent != null || futureOrPresent2 != null) { constraints.add("future or present"); } if (constraints.isEmpty()) { return null; } StringBuilder builder = new StringBuilder(); Iterator it = constraints.iterator(); while (it.hasNext()) { String token = it.next(); builder.append(token); if (it.hasNext()) { builder.append(", "); } } return builder.toString(); } private static String describeTypeIfPrimitive(Element el) { final TypeMirror type = el.asType(); if (type instanceof PrimitiveType) { return " " + type.getKind().name().toLowerCase(); } else { switch (type.toString()) { case "java.lang.Integer": return " int"; case "java.lang.Short": return " short"; case "java.lang.Float": return " float"; case "java.lang.Double": return " double"; case "java.lang.Long": return " long"; case "java.lang.Character": return " char"; case "java.lang.Byte": return " byte"; case "java.lang.Boolean": return " boolean"; } } return ""; } }





© 2015 - 2025 Weber Informatics LLC | Privacy Policy