You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@sling.apache.org by cz...@apache.org on 2020/11/07 14:29:16 UTC
[sling-org-apache-sling-feature-extension-apiregions] branch
SLING-9867 updated: Add validator tests
This is an automated email from the ASF dual-hosted git repository.
cziegeler pushed a commit to branch SLING-9867
in repository https://gitbox.apache.org/repos/asf/sling-org-apache-sling-feature-extension-apiregions.git
The following commit(s) were added to refs/heads/SLING-9867 by this push:
new 522ca6c Add validator tests
522ca6c is described below
commit 522ca6c8ec9a857f003af39c26e831fafb7b0c52
Author: Carsten Ziegeler <cz...@apache.org>
AuthorDate: Sat Nov 7 15:28:50 2020 +0100
Add validator tests
---
.../apiregions/api/config/PropertyType.java | 4 +-
.../extension/apiregions/api/config/Validator.java | 193 ++++++-----
.../apiregions/api/config/ValidatorTest.java | 379 +++++++++++++++++++++
3 files changed, 487 insertions(+), 89 deletions(-)
diff --git a/src/main/java/org/apache/sling/feature/extension/apiregions/api/config/PropertyType.java b/src/main/java/org/apache/sling/feature/extension/apiregions/api/config/PropertyType.java
index e0d2889..fd8e971 100644
--- a/src/main/java/org/apache/sling/feature/extension/apiregions/api/config/PropertyType.java
+++ b/src/main/java/org/apache/sling/feature/extension/apiregions/api/config/PropertyType.java
@@ -23,9 +23,9 @@ public enum PropertyType {
STRING,
LONG,
- INT,
+ INTEGER,
SHORT,
- CHAR,
+ CHARACTER,
BYTE,
DOUBLE,
FLOAT,
diff --git a/src/main/java/org/apache/sling/feature/extension/apiregions/api/config/Validator.java b/src/main/java/org/apache/sling/feature/extension/apiregions/api/config/Validator.java
index 6a3eda6..1a21b21 100644
--- a/src/main/java/org/apache/sling/feature/extension/apiregions/api/config/Validator.java
+++ b/src/main/java/org/apache/sling/feature/extension/apiregions/api/config/Validator.java
@@ -65,41 +65,11 @@ public class Validator {
}
if ( values != null ) {
- // array or collection
- if ( prop.getCardinality() > 0 && values.size() > prop.getCardinality() ) {
- messages.add("Array/collection contains too many elements, only " + prop.getCardinality() + " allowed");
- }
- for(final Object val : values) {
- validateValue(prop, val, messages);
- }
- if ( prop.getIncludes() != null ) {
- for(final String inc : prop.getIncludes()) {
- boolean found = false;
- for(final Object val : values) {
- if ( inc.equals(val.toString())) {
- found = true;
- break;
- }
- }
- if ( !found ) {
- messages.add("Required included value " + inc + " not found");
- }
- }
- }
- if ( prop.getExcludes() != null ) {
- for(final String exc : prop.getExcludes()) {
- boolean found = false;
- for(final Object val : values) {
- if ( exc.equals(val.toString())) {
- found = true;
- break;
- }
- }
- if ( found ) {
- messages.add("Required excluded value " + exc + " found");
- }
- }
- }
+ // array or collection
+ for(final Object val : values) {
+ validateValue(prop, val, messages);
+ }
+ validateList(prop, values, messages);
}
}
return new ValidationResult(){
@@ -114,6 +84,40 @@ public class Validator {
};
}
+ static void validateList(final Property prop, final List<Object> values, final List<String> messages) {
+ if ( prop.getCardinality() > 0 && values.size() > prop.getCardinality() ) {
+ messages.add("Array/collection contains too many elements, only " + prop.getCardinality() + " allowed");
+ }
+ if ( prop.getIncludes() != null ) {
+ for(final String inc : prop.getIncludes()) {
+ boolean found = false;
+ for(final Object val : values) {
+ if ( inc.equals(val.toString())) {
+ found = true;
+ break;
+ }
+ }
+ if ( !found ) {
+ messages.add("Required included value " + inc + " not found");
+ }
+ }
+ }
+ if ( prop.getExcludes() != null ) {
+ for(final String exc : prop.getExcludes()) {
+ boolean found = false;
+ for(final Object val : values) {
+ if ( exc.equals(val.toString())) {
+ found = true;
+ break;
+ }
+ }
+ if ( found ) {
+ messages.add("Required excluded value " + exc + " found");
+ }
+ }
+ }
+ }
+
static void validateValue(final Property prop, final Object value, final List<String> messages) {
if ( value != null ) {
switch ( prop.getType() ) {
@@ -121,13 +125,13 @@ public class Validator {
break;
case BYTE : validateByte(prop, value, messages);
break;
- case CHAR : validateChar(prop, value, messages);
+ case CHARACTER : validateCharacter(prop, value, messages);
break;
case DOUBLE : validateDouble(prop, value, messages);
break;
case FLOAT : validateFloat(prop, value, messages);
break;
- case INT : validateInt(prop, value, messages);
+ case INTEGER : validateInteger(prop, value, messages);
break;
case LONG : validateLong(prop, value, messages);
break;
@@ -142,23 +146,9 @@ public class Validator {
case URL : validateURL(prop, value, messages);
break;
default : messages.add("Unable to validate value - unknown property type : " + prop.getType());
- }
- if ( prop.getRegexPattern() != null ) {
- if ( !prop.getRegexPattern().matcher(value.toString()).matches() ) {
- messages.add("Value " + value + " does not match regex " + prop.getRegex());
- }
- }
- if ( prop.getOptions() != null ) {
- boolean found = false;
- for(final Option opt : prop.getOptions()) {
- if ( opt.getValue().equals(value.toString() ) ) {
- found = true;
- }
- }
- if ( !found ) {
- messages.add("Value " + value + " does not match provided options");
- }
- }
+ }
+ validateRegex(prop, value, messages);
+ validateOptions(prop, value, messages);
} else {
messages.add("Null value provided for validation");
}
@@ -185,7 +175,9 @@ public class Validator {
validateRange(prop, Byte.valueOf(v), messages);
} catch ( final NumberFormatException nfe ) {
messages.add("Value is not a valid Byte : " + value);
- }
+ }
+ } else if ( value instanceof Number ) {
+ validateRange(prop, ((Number)value).byteValue(), messages);
} else {
messages.add("Byte value must either be of type Byte or String : " + value);
}
@@ -203,6 +195,8 @@ public class Validator {
} catch ( final NumberFormatException nfe ) {
messages.add("Value is not a valid Short : " + value);
}
+ } else if ( value instanceof Number ) {
+ validateRange(prop, ((Number)value).shortValue(), messages);
} else {
messages.add("Short value must either be of type Short or String : " + value);
}
@@ -211,7 +205,7 @@ public class Validator {
}
}
- static void validateInt(final Property prop, final Object value, final List<String> messages) {
+ static void validateInteger(final Property prop, final Object value, final List<String> messages) {
if ( ! (value instanceof Integer) ) {
if ( value instanceof String ) {
final String v = (String)value;
@@ -220,6 +214,8 @@ public class Validator {
} catch ( final NumberFormatException nfe ) {
messages.add("Value is not a valid Integer : " + value);
}
+ } else if ( value instanceof Number ) {
+ validateRange(prop, ((Number)value).intValue(), messages);
} else {
messages.add("Integer value must either be of type Integer or String : " + value);
}
@@ -237,6 +233,8 @@ public class Validator {
} catch ( final NumberFormatException nfe ) {
messages.add("Value is not a valid Long : " + value);
}
+ } else if ( value instanceof Number ) {
+ validateRange(prop, ((Number)value).longValue(), messages);
} else {
messages.add("Long value must either be of type Long or String : " + value);
}
@@ -254,6 +252,8 @@ public class Validator {
} catch ( final NumberFormatException nfe ) {
messages.add("Value is not a valid Float : " + value);
}
+ } else if ( value instanceof Number ) {
+ validateRange(prop, ((Number)value).floatValue(), messages);
} else {
messages.add("Float value must either be of type Float or String : " + value);
}
@@ -271,6 +271,8 @@ public class Validator {
} catch ( final NumberFormatException nfe ) {
messages.add("Value is not a valid Double : " + value);
}
+ } else if ( value instanceof Number ) {
+ validateRange(prop, ((Number)value).doubleValue(), messages);
} else {
messages.add("Double value must either be of type Double or String : " + value);
}
@@ -279,7 +281,7 @@ public class Validator {
}
}
- static void validateChar(final Property prop, final Object value, final List<String> messages) {
+ static void validateCharacter(final Property prop, final Object value, final List<String> messages) {
if ( ! (value instanceof Character) ) {
if ( value instanceof String ) {
final String v = (String)value;
@@ -317,37 +319,54 @@ public class Validator {
static void validateRange(final Property prop, final Number value, final List<String> messages) {
if ( prop.getRange() != null ) {
- try {
- if ( prop.getRange().getMin() != null ) {
- if ( value instanceof Float || value instanceof Double ) {
- final double min = prop.getRange().getMin().doubleValue();
- if ( value.doubleValue() < min ) {
- messages.add("Value " + value + " is too low; should not be lower than " + prop.getRange().getMin());
- }
- } else {
- final long min = prop.getRange().getMin().longValue();
- if ( value.longValue() < min ) {
- messages.add("Value " + value + " is too low; should not be lower than " + prop.getRange().getMin());
- }
- }
- }
- if ( prop.getRange().getMax() != null ) {
- if ( value instanceof Float || value instanceof Double ) {
- final double max = prop.getRange().getMax().doubleValue();
- if ( value.doubleValue() > max ) {
- messages.add("Value " + value + " is too high; should not be higher than " + prop.getRange().getMax());
- }
- } else {
- final long max = prop.getRange().getMax().longValue();
- if ( value.longValue() > max ) {
- messages.add("Value " + value + " is too high; should not be higher than " + prop.getRange().getMax());
- }
- }
- }
- } catch ( final NumberFormatException nfe) {
- messages.add("Invalid range specified in " + prop.getRange());
- }
+ if ( prop.getRange().getMin() != null ) {
+ if ( value instanceof Float || value instanceof Double ) {
+ final double min = prop.getRange().getMin().doubleValue();
+ if ( value.doubleValue() < min ) {
+ messages.add("Value " + value + " is too low; should not be lower than " + prop.getRange().getMin());
+ }
+ } else {
+ final long min = prop.getRange().getMin().longValue();
+ if ( value.longValue() < min ) {
+ messages.add("Value " + value + " is too low; should not be lower than " + prop.getRange().getMin());
+ }
+ }
+ }
+ if ( prop.getRange().getMax() != null ) {
+ if ( value instanceof Float || value instanceof Double ) {
+ final double max = prop.getRange().getMax().doubleValue();
+ if ( value.doubleValue() > max ) {
+ messages.add("Value " + value + " is too high; should not be higher than " + prop.getRange().getMax());
+ }
+ } else {
+ final long max = prop.getRange().getMax().longValue();
+ if ( value.longValue() > max ) {
+ messages.add("Value " + value + " is too high; should not be higher than " + prop.getRange().getMax());
+ }
+ }
+ }
}
}
+ static void validateRegex(final Property prop, final Object value, final List<String> messages) {
+ if ( prop.getRegexPattern() != null ) {
+ if ( !prop.getRegexPattern().matcher(value.toString()).matches() ) {
+ messages.add("Value " + value + " does not match regex " + prop.getRegex());
+ }
+ }
+ }
+
+ static void validateOptions(final Property prop, final Object value, final List<String> messages) {
+ if ( prop.getOptions() != null ) {
+ boolean found = false;
+ for(final Option opt : prop.getOptions()) {
+ if ( opt.getValue().equals(value.toString() ) ) {
+ found = true;
+ }
+ }
+ if ( !found ) {
+ messages.add("Value " + value + " does not match provided options");
+ }
+ }
+ }
}
\ No newline at end of file
diff --git a/src/test/java/org/apache/sling/feature/extension/apiregions/api/config/ValidatorTest.java b/src/test/java/org/apache/sling/feature/extension/apiregions/api/config/ValidatorTest.java
new file mode 100644
index 0000000..1bfff16
--- /dev/null
+++ b/src/test/java/org/apache/sling/feature/extension/apiregions/api/config/ValidatorTest.java
@@ -0,0 +1,379 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You 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 org.apache.sling.feature.extension.apiregions.api.config;
+
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertTrue;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import org.junit.Test;
+
+public class ValidatorTest {
+
+ @Test public void testValidateValueWithNull() {
+ final List<String> messages = new ArrayList<>();
+ Validator.validateValue(null, null, messages);
+ assertEquals(1, messages.size());
+ messages.clear();
+ }
+
+ @Test public void testValidateBoolean() {
+ final Property prop = new Property();
+ prop.setType(PropertyType.BOOLEAN);
+
+ final List<String> messages = new ArrayList<>();
+
+ Validator.validateBoolean(prop, Boolean.TRUE, messages);
+ assertTrue(messages.isEmpty());
+
+ Validator.validateBoolean(prop, Boolean.FALSE, messages);
+ assertTrue(messages.isEmpty());
+
+ Validator.validateBoolean(prop, "TRUE", messages);
+ assertTrue(messages.isEmpty());
+
+ Validator.validateBoolean(prop, "FALSE", messages);
+ assertTrue(messages.isEmpty());
+
+ Validator.validateBoolean(prop, "yes", messages);
+ assertEquals(1, messages.size());
+ messages.clear();
+
+ Validator.validateBoolean(prop, 1, messages);
+ assertEquals(1, messages.size());
+ messages.clear();
+ }
+
+ @Test public void testValidateByte() {
+ final Property prop = new Property();
+ prop.setType(PropertyType.BYTE);
+
+ final List<String> messages = new ArrayList<>();
+
+ Validator.validateByte(prop, (byte)1, messages);
+ assertTrue(messages.isEmpty());
+
+ Validator.validateByte(prop, "1", messages);
+ assertTrue(messages.isEmpty());
+
+ Validator.validateByte(prop, "yes", messages);
+ assertEquals(1, messages.size());
+ messages.clear();
+
+ Validator.validateByte(prop, 1, messages);
+ assertTrue(messages.isEmpty());
+ }
+
+ @Test public void testValidateShort() {
+ final Property prop = new Property();
+ prop.setType(PropertyType.SHORT);
+
+ final List<String> messages = new ArrayList<>();
+
+ Validator.validateShort(prop, (short)1, messages);
+ assertTrue(messages.isEmpty());
+
+ Validator.validateShort(prop, "1", messages);
+ assertTrue(messages.isEmpty());
+
+ Validator.validateShort(prop, "yes", messages);
+ assertEquals(1, messages.size());
+ messages.clear();
+
+ Validator.validateShort(prop, 1, messages);
+ assertTrue(messages.isEmpty());
+ }
+
+ @Test public void testValidateInteger() {
+ final Property prop = new Property();
+ prop.setType(PropertyType.INTEGER);
+
+ final List<String> messages = new ArrayList<>();
+
+ Validator.validateInteger(prop, 1, messages);
+ assertTrue(messages.isEmpty());
+
+ Validator.validateInteger(prop, "1", messages);
+ assertTrue(messages.isEmpty());
+
+ Validator.validateInteger(prop, "yes", messages);
+ assertEquals(1, messages.size());
+ messages.clear();
+
+ Validator.validateInteger(prop, 1, messages);
+ assertTrue(messages.isEmpty());
+ }
+
+ @Test public void testValidateLong() {
+ final Property prop = new Property();
+ prop.setType(PropertyType.LONG);
+
+ final List<String> messages = new ArrayList<>();
+
+ Validator.validateLong(prop, 1L, messages);
+ assertTrue(messages.isEmpty());
+
+ Validator.validateLong(prop, "1", messages);
+ assertTrue(messages.isEmpty());
+
+ Validator.validateLong(prop, "yes", messages);
+ assertEquals(1, messages.size());
+ messages.clear();
+
+ Validator.validateLong(prop, 1, messages);
+ assertTrue(messages.isEmpty());
+ }
+
+ @Test public void testValidateFloat() {
+ final Property prop = new Property();
+ prop.setType(PropertyType.FLOAT);
+
+ final List<String> messages = new ArrayList<>();
+
+ Validator.validateFloat(prop, 1.1, messages);
+ assertTrue(messages.isEmpty());
+
+ Validator.validateFloat(prop, "1.1", messages);
+ assertTrue(messages.isEmpty());
+
+ Validator.validateFloat(prop, "yes", messages);
+ assertEquals(1, messages.size());
+ messages.clear();
+
+ Validator.validateFloat(prop, 1, messages);
+ assertTrue(messages.isEmpty());
+ }
+
+ @Test public void testValidateDouble() {
+ final Property prop = new Property();
+ prop.setType(PropertyType.DOUBLE);
+
+ final List<String> messages = new ArrayList<>();
+
+ Validator.validateDouble(prop, 1.1d, messages);
+ assertTrue(messages.isEmpty());
+
+ Validator.validateDouble(prop, "1.1", messages);
+ assertTrue(messages.isEmpty());
+
+ Validator.validateDouble(prop, "yes", messages);
+ assertEquals(1, messages.size());
+ messages.clear();
+
+ Validator.validateDouble(prop, 1, messages);
+ assertTrue(messages.isEmpty());
+ }
+
+ @Test public void testValidateChar() {
+ final Property prop = new Property();
+ prop.setType(PropertyType.CHARACTER);
+
+ final List<String> messages = new ArrayList<>();
+
+ Validator.validateCharacter(prop, 'x', messages);
+ assertTrue(messages.isEmpty());
+
+ Validator.validateCharacter(prop, "y", messages);
+ assertTrue(messages.isEmpty());
+
+ Validator.validateCharacter(prop, "yes", messages);
+ assertEquals(1, messages.size());
+ messages.clear();
+ }
+
+ @Test public void testValidateUrl() {
+ final List<String> messages = new ArrayList<>();
+
+ Validator.validateURL(null, "https://sling.apache.org/documentation", messages);
+ assertTrue(messages.isEmpty());
+
+ Validator.validateURL(null, "hello world", messages);
+ assertEquals(1, messages.size());
+ messages.clear();
+ }
+
+ @Test public void testValidateEmail() {
+ final List<String> messages = new ArrayList<>();
+
+ Validator.validateEmail(null, "a@b.com", messages);
+ assertTrue(messages.isEmpty());
+
+ Validator.validateEmail(null, "hello world", messages);
+ assertEquals(1, messages.size());
+ messages.clear();
+ }
+
+ @Test public void testValidatePassword() {
+ final Property prop = new Property();
+ final List<String> messages = new ArrayList<>();
+
+ Validator.validatePassword(prop, null, messages);
+ assertEquals(1, messages.size());
+ messages.clear();
+
+ prop.setVariable("secret");
+ Validator.validatePassword(prop, null, messages);
+ assertTrue(messages.isEmpty());
+ }
+
+ @Test public void testValidateRange() {
+ final List<String> messages = new ArrayList<>();
+ final Property prop = new Property();
+
+ // no range set
+ Validator.validateRange(prop, 2, messages);
+ assertTrue(messages.isEmpty());
+
+ // empty range set
+ prop.setRange(new Range());
+ Validator.validateRange(prop, 2, messages);
+ assertTrue(messages.isEmpty());
+
+ // min set
+ prop.getRange().setMin(5);
+ Validator.validateRange(prop, 5, messages);
+ assertTrue(messages.isEmpty());
+ Validator.validateRange(prop, 6, messages);
+ assertTrue(messages.isEmpty());
+ Validator.validateRange(prop, 4, messages);
+ assertEquals(1, messages.size());
+ messages.clear();
+
+ Validator.validateRange(prop, 5.0, messages);
+ assertTrue(messages.isEmpty());
+ Validator.validateRange(prop, 6.0, messages);
+ assertTrue(messages.isEmpty());
+ Validator.validateRange(prop, 4.0, messages);
+ assertEquals(1, messages.size());
+ messages.clear();
+
+ // max set
+ prop.getRange().setMax(6);
+ Validator.validateRange(prop, 5, messages);
+ assertTrue(messages.isEmpty());
+ Validator.validateRange(prop, 6, messages);
+ assertTrue(messages.isEmpty());
+ Validator.validateRange(prop, 7, messages);
+ assertEquals(1, messages.size());
+ messages.clear();
+
+ Validator.validateRange(prop, 5.0, messages);
+ assertTrue(messages.isEmpty());
+ Validator.validateRange(prop, 6.0, messages);
+ assertTrue(messages.isEmpty());
+ Validator.validateRange(prop, 7.0, messages);
+ assertEquals(1, messages.size());
+ messages.clear();
+ }
+
+ @Test public void testValidateRegex() {
+ final List<String> messages = new ArrayList<>();
+ final Property prop = new Property();
+
+ // no regex
+ Validator.validateRegex(prop, "hello world", messages);
+ Validator.validateRegex(prop, "world", messages);
+ assertTrue(messages.isEmpty());
+
+ // regex
+ prop.setRegex("h(.*)");
+ Validator.validateRegex(prop, "hello world", messages);
+ assertTrue(messages.isEmpty());
+ Validator.validateRegex(prop, "world", messages);
+ assertEquals(1, messages.size());
+ messages.clear();
+ }
+
+ @Test public void testValidateOptions() {
+ final List<String> messages = new ArrayList<>();
+ final Property prop = new Property();
+
+ // no options
+ Validator.validateOptions(prop, "foo", messages);
+ Validator.validateOptions(prop, "bar", messages);
+ assertTrue(messages.isEmpty());
+
+ // options
+ final List<Option> options = new ArrayList<>();
+ final Option o1 = new Option();
+ o1.setValue("foo");
+ final Option o2 = new Option();
+ o2.setValue("7");
+ options.add(o1);
+ options.add(o2);
+ prop.setOptions(options);
+ Validator.validateOptions(prop, "foo", messages);
+ assertTrue(messages.isEmpty());
+ Validator.validateOptions(prop, "bar", messages);
+ assertEquals(1, messages.size());
+ messages.clear();
+ Validator.validateOptions(prop, 7, messages);
+ assertTrue(messages.isEmpty());
+ }
+
+ @Test public void testValidateList() {
+ final List<String> messages = new ArrayList<>();
+ final Property prop = new Property();
+
+ final List<Object> values = new ArrayList<>();
+ values.add("a");
+ values.add("b");
+ values.add("c");
+
+ // default cardinality - no excludes/includes
+ Validator.validateList(prop, values, messages);
+ assertEquals(1, messages.size());
+ messages.clear();
+
+ // cardinality 3 - no excludes/includes
+ prop.setCardinality(3);
+ Validator.validateList(prop, values, messages);
+ assertTrue(messages.isEmpty());
+
+ values.add("d");
+ Validator.validateList(prop, values, messages);
+ assertEquals(1, messages.size());
+ messages.clear();
+
+ // excludes
+ prop.setExcludes(new String[] {"d", "e"});
+ Validator.validateList(prop, values, messages);
+ assertEquals(2, messages.size()); // cardinality and exclude
+ messages.clear();
+
+ values.remove("d");
+ Validator.validateList(prop, values, messages);
+ assertTrue(messages.isEmpty());
+
+ // includes
+ prop.setIncludes(new String[] {"b"});
+ Validator.validateList(prop, values, messages);
+ assertTrue(messages.isEmpty());
+
+ prop.setIncludes(new String[] {"x"});
+ Validator.validateList(prop, values, messages);
+ assertEquals(1, messages.size());
+ messages.clear();
+
+ values.add("x");
+ values.remove("a");
+ Validator.validateList(prop, values, messages);
+ assertTrue(messages.isEmpty());
+ }
+}