blob: 8f571fbf8332f553398cd89ea9b4d9327d04884e [file] [log] [blame]
/*
* 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.bval.jsr303;
import java.lang.reflect.Array;
import java.lang.reflect.InvocationTargetException;
import java.util.ArrayList;
import java.util.Collections;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Locale;
import java.util.Map;
import java.util.Set;
import javax.validation.ConstraintViolation;
import javax.validation.Validation;
import javax.validation.Validator;
import javax.validation.ValidatorFactory;
import javax.validation.constraints.NotNull;
import javax.validation.constraints.Size;
import javax.validation.groups.Default;
import javax.validation.metadata.BeanDescriptor;
import javax.validation.metadata.ConstraintDescriptor;
import javax.validation.metadata.PropertyDescriptor;
import junit.framework.Assert;
import junit.framework.TestCase;
import org.apache.bval.constraints.NotNullValidator;
import org.apache.bval.jsr303.example.AccessTestBusinessObject;
import org.apache.bval.jsr303.example.AccessTestBusinessObjectSub;
import org.apache.bval.jsr303.example.Address;
import org.apache.bval.jsr303.example.Author;
import org.apache.bval.jsr303.example.Book;
import org.apache.bval.jsr303.example.BusinessAddress;
import org.apache.bval.jsr303.example.Continent;
import org.apache.bval.jsr303.example.Country;
import org.apache.bval.jsr303.example.First;
import org.apache.bval.jsr303.example.Last;
import org.apache.bval.jsr303.example.RecursiveFoo;
import org.apache.bval.jsr303.util.TestUtils;
/**
* Description: <br/>
*/
public class ValidationTest extends TestCase {
static ValidatorFactory factory;
static {
factory = Validation.buildDefaultValidatorFactory();
((DefaultMessageInterpolator) factory.getMessageInterpolator()).setLocale(Locale.ENGLISH);
}
/**
* Validator instance to test
*/
protected Validator validator;
/**
* {@inheritDoc}
*/
@Override
public void setUp() throws Exception {
super.setUp();
validator = createValidator();
}
/**
* Create the validator instance.
*
* @return Validator
*/
protected Validator createValidator() {
return factory.getValidator();
}
public void testAccessStrategies_field_method() {
AccessTestBusinessObject o1 = new AccessTestBusinessObject("1");
AccessTestBusinessObjectSub o2 = new AccessTestBusinessObjectSub("3");
Set<ConstraintViolation<AccessTestBusinessObject>> errors = validator.validate(o1);
assertTrue(errors.isEmpty());
Set<ConstraintViolation<AccessTestBusinessObjectSub>> errors2 = validator.validate(o2);
assertTrue(errors2.isEmpty());
o2 = new AccessTestBusinessObjectSub("1");
errors2 = validator.validate(o2);
assertEquals(1, errors2.size());
// assert, that getvar2() and getVar2() are both validated with their
// getter method
o2 = new AccessTestBusinessObjectSub("3");
o2.setVar2("1");
o2.setvar2("2");
errors2 = validator.validate(o2);
assertEquals(2, errors2.size());
o2.setvar2("5");
o2.setVar2("6");
errors2 = validator.validate(o2);
assertEquals(0, errors2.size());
o2.setvar2("5");
o2.setVar2("-1");
errors2 = validator.validate(o2);
assertEquals(1, errors2.size());
}
public void testAccessStrategies_on_children() {
AccessTestBusinessObject o1 = new AccessTestBusinessObject("1");
AccessTestBusinessObject o2 = new AccessTestBusinessObject("2");
o1.next(o2);
Set<ConstraintViolation<AccessTestBusinessObject>> errors = validator.validate(o1);
// assert, that field access 'next' is used and not getNext() is
// called!!!
assertEquals(1, errors.size());
o2 = new AccessTestBusinessObject("1");
o1.next(o2);
errors = validator.validate(o1);
assertEquals(0, errors.size());
// assert that toBeIgnored not validated, because not annotated with
// @Valid
o1.setToBeIgnored(new AccessTestBusinessObject("99"));
errors = validator.validate(o1);
assertEquals(0, errors.size());
o1.setNext(new AccessTestBusinessObject("99"));
errors = validator.validate(o1);
assertEquals(1, errors.size());
}
public void testBook() {
Author author = new Author();
author.setLastName("Baudelaire");
author.setFirstName("");
Book book = new Book();
book.setAuthor(author);
book.setSubtitle("12345678900125678901234578901234567890");
// NotEmpty failure on the title field
Set<ConstraintViolation<Book>> errors = validator.validate(book, Book.All.class);
Assert.assertTrue(!errors.isEmpty());
book.setTitle("Les fleurs du mal");
author.setCompany("Some random publisher with a very very very long name");
// author.firstName fails to pass the NotEmpty constraint
// author.company fails to pass the Size constraint
}
/**
* test: - dynamic resolution of associated object types. - inheritance of validation constraints - complex
* valiation, different groups, nested object net
*/
public void testValidAnnotation() {
Author a = new Author();
a.setAddresses(new ArrayList<Address>());
BusinessAddress adr = new BusinessAddress();
adr.setCountry(new Country());
adr.setAddressline1("line1");
adr.setAddressline2("line2");
adr.setZipCode("1234567890123456789");
a.getAddresses().add(adr);
a.setFirstName("Karl");
a.setLastName("May");
Set<ConstraintViolation<Author>> found = validator.validate(a, Default.class, First.class, Last.class);
Assert.assertTrue(!found.isEmpty());
Assert.assertEquals(4, found.size());
adr.setCity("Berlin");
adr.setZipCode("12345");
adr.setCompany("apache");
found = validator.validate(a, Default.class, First.class, Last.class);
Assert.assertEquals(1, found.size());
ConstraintViolation<Author> ic = found.iterator().next();
Assert.assertEquals("addresses[0].country.name", ic.getPropertyPath().toString());
}
public void testPropertyPathWithIndex() {
Author a = new Author();
a.setAddresses(new ArrayList<Address>());
Address adr = new Address();
adr.setAddressline1("adr1");
adr.setCity("Santiago");
a.getAddresses().add(adr);
adr = new Address();
adr.setAddressline1("adr2");
adr.setCity("Havanna");
a.getAddresses().add(adr);
adr = new Address();
adr.setAddressline1("adr3");
adr.setCity("Trinidad");
a.getAddresses().add(adr);
Set<ConstraintViolation<Author>> constraints = validator.validate(a);
Assert.assertTrue(!constraints.isEmpty());
assertPropertyPath("addresses[0].country", constraints);
assertPropertyPath("addresses[1].country", constraints);
assertPropertyPath("addresses[2].country", constraints);
}
/**
* Check correct path reporting when validating a set of beans.
*/
public void testPropertyPathOnSet() {
Continent c = new Continent();
c.name = "c1";
Country country = new Country();
country.setISO2Code("xx");
country.setISO3Code("xxx");
country.setName(null);
c.countries.add(country);
Set<ConstraintViolation<Continent>> constraints = validator.validate(c);
Assert.assertEquals("Incorrect number of violations detected", 1, constraints.size());
assertPropertyPath("countries[].name", constraints);
}
private <T> void assertPropertyPath(String propertyPath, Set<ConstraintViolation<T>> constraints) {
for (ConstraintViolation<T> each : constraints) {
if (each.getPropertyPath().toString().equals(propertyPath))
return;
}
Assert.fail(propertyPath + " not found in " + constraints);
}
public void testPropertyPathRecursive() {
RecursiveFoo foo1 = new RecursiveFoo(); // root
RecursiveFoo foo11 = new RecursiveFoo();
foo1.getFoos().add(foo11); // foos[0]
RecursiveFoo foo12 = new RecursiveFoo();
foo1.getFoos().add(foo12); // foos[1]
RecursiveFoo foo2 = new RecursiveFoo();
foo11.getFoos().add(foo2); // foos[0].foos[0]
Set<ConstraintViolation<RecursiveFoo>> constraints = validator.validate(foo1);
assertPropertyPath("foos[0].foos[0].foos", constraints);
assertPropertyPath("foos[1].foos", constraints);
}
public void testNullElementInCollection() {
try {
validator.validate(null);
Assert.fail();
} catch (IllegalArgumentException ex) {
}
RecursiveFoo foo = new RecursiveFoo();
foo.getFoos().add(new RecursiveFoo());
foo.getFoos().add(null);
Assert.assertTrue(!validator.validate(foo).isEmpty());
// check that no nullpointer exception gets thrown
}
public void testGroups() {
Author author = new Author();
author.setCompany("ACME");
Book book = new Book();
book.setTitle("");
book.setAuthor(author);
boolean foundTitleConstraint = false;
Set<ConstraintViolation<Book>> constraintViolations = validator.validate(book, Book.All.class);
assertEquals(1, constraintViolations.size());
// assuming an english locale, the interpolated message is returned
for (ConstraintViolation<Book> constraintViolation : constraintViolations) {
if (constraintViolation.getRootBean().getClass() == Book.class) {
Assert.assertEquals("may not be empty", constraintViolation.getMessage());
Assert.assertTrue(book == constraintViolation.getRootBean());
// the offending property
if (constraintViolation.getPropertyPath().toString().equals("title")) {
foundTitleConstraint = true;
// the offending value
Assert.assertEquals(book.getTitle(), constraintViolation.getInvalidValue());
}
}
}
Assert.assertTrue(foundTitleConstraint);
}
/**
* Example 2.14. Using the fluent API to build custom constraint violations. test that: the
* {@link org.apache.bval.constraints.ZipCodeCityCoherenceValidator} adds custom messages to the context and
* suppresses the default message
*/
public void testConstraintValidatorContextFluentAPI() {
Address ad = new Address();
ad.setCity("error");
ad.setZipCode("error");
ad.setAddressline1("something");
ad.setCountry(new Country());
ad.getCountry().setName("something");
Set<ConstraintViolation<Address>> violations = validator.validate(ad);
Assert.assertEquals(2, violations.size());
for (ConstraintViolation<Address> each : violations) {
Assert.assertTrue(each.getMessage().endsWith(" not OK"));
}
assertNotNull(TestUtils.getViolation(violations, "city"));
assertNotNull(TestUtils.getViolation(violations, ""));
}
public void testValidateNestedPropertyPath() throws InvocationTargetException, NoSuchMethodException,
IllegalAccessException {
final String propPath = "addresses[0].country.ISO2Code";
Author author = new Author();
author.setAddresses(new ArrayList<Address>());
Address adr = new Address();
author.getAddresses().add(adr);
Country country = new Country();
adr.setCountry(country);
country.setISO2Code("too_long");
Set<ConstraintViolation<Author>> iv = validator.validateProperty(author, propPath);
Assert.assertEquals(1, iv.size());
ConstraintViolation<Author> vio = iv.iterator().next();
assertEquals(propPath, vio.getPropertyPath().toString());
assertSame(author, vio.getRootBean());
assertSame(author.getAddresses().get(0).getCountry(), vio.getLeafBean());
country.setISO2Code("23");
iv = validator.validateProperty(author, propPath);
Assert.assertEquals(0, iv.size());
iv = validator.validateValue(Author.class, propPath, "345");
Assert.assertEquals(1, iv.size());
vio = iv.iterator().next();
assertEquals(propPath, vio.getPropertyPath().toString());
assertNull(vio.getRootBean());
assertNull(vio.getLeafBean());
iv = validator.validateValue(Author.class, propPath, "34");
Assert.assertEquals(0, iv.size());
}
public void testValidateCascadingNestedBean() throws InvocationTargetException, NoSuchMethodException,
IllegalAccessException {
final String propPath = "addresses[0]";
CascadingPropertyValidator v = validator.unwrap(CascadingPropertyValidator.class);
Author author = new Author();
author.setAddresses(new ArrayList<Address>());
Address adr = new Address();
author.getAddresses().add(adr);
Country country = new Country();
adr.setCity("dark");
adr.setCountry(country);
Set<ConstraintViolation<Author>> iv = v.validateProperty(author, propPath);
Assert.assertEquals(1, iv.size()); // null address line 1 (no cascade)
country.setISO2Code("too_long");
iv = v.validateProperty(author, propPath, true);
Assert.assertEquals(3, iv.size()); // null address line 1 + null
// country.name + too long
// country.iso2code
country.setISO2Code("23");
iv = v.validateProperty(author, propPath, true);
Assert.assertEquals(2, iv.size()); // null address line 1 + null
// country.name, country.iso2code
// fixed
Address value = new Address();
value.setCity("whatever");
value.setAddressline1("1 address line");
iv = v.validateValue(Author.class, propPath, value, true);
Assert.assertEquals(1, iv.size()); // null country
value.setCountry(new Country());
iv = v.validateValue(Author.class, propPath, value, true);
Assert.assertEquals(1, iv.size()); // null country.name
value.getCountry().setName("NWO");
iv = v.validateValue(Author.class, propPath, value, true);
Assert.assertEquals(0, iv.size());
}
public void testValidateCascadingNestedProperty() throws InvocationTargetException, NoSuchMethodException,
IllegalAccessException {
final String propPath = "addresses[0].country";
CascadingPropertyValidator v = validator.unwrap(CascadingPropertyValidator.class);
Author author = new Author();
author.setAddresses(new ArrayList<Address>());
Address adr = new Address();
author.getAddresses().add(adr);
Country country = new Country();
adr.setCity("dark");
adr.setCountry(country);
Set<ConstraintViolation<Author>> iv = v.validateProperty(author, propPath);
Assert.assertEquals(0, iv.size());
country.setISO2Code("too_long");
iv = v.validateProperty(author, propPath, true);
Assert.assertEquals(2, iv.size());
// country.name + too long
// country.iso2code
country.setISO2Code("23");
iv = v.validateProperty(author, propPath, true);
Assert.assertEquals(1, iv.size());
// country.name, country.iso2code
Country value = null;
iv = v.validateValue(Author.class, propPath, value, true);
Assert.assertEquals(1, iv.size()); // null country
value = new Country();
iv = v.validateValue(Author.class, propPath, value, true);
Assert.assertEquals(1, iv.size()); // null country.name
value.setName("NWO");
iv = v.validateValue(Author.class, propPath, value, true);
Assert.assertEquals(0, iv.size());
}
public void testValidateCascadingNestedTipProperty() {
final String propPath = "addresses[0].country.name";
CascadingPropertyValidator v = validator.unwrap(CascadingPropertyValidator.class);
Author author = new Author();
author.setAddresses(new ArrayList<Address>());
Address adr = new Address();
author.getAddresses().add(adr);
Country country = new Country();
adr.setCity("dark");
adr.setCountry(country);
Set<ConstraintViolation<Author>> iv = v.validateProperty(author, propPath);
Assert.assertEquals(1, iv.size());
iv = v.validateProperty(author, propPath, true);
Assert.assertEquals(1, iv.size());
}
public void testValidateCascadingKeyedElement() throws InvocationTargetException, NoSuchMethodException,
IllegalAccessException {
final String propPath = "[foo]";
CascadingPropertyValidator v = validator.unwrap(CascadingPropertyValidator.class);
final Address adr = new Address();
@SuppressWarnings("serial")
Object map = new HashMap<String, Address>() {
{
put("foo", adr);
}
};
Country country = new Country();
adr.setCity("dark");
adr.setCountry(country);
Set<ConstraintViolation<Object>> iv = v.validateProperty(map, propPath);
Assert.assertEquals(1, iv.size()); // null address line 1 (no cascade)
country.setISO2Code("too_long");
iv = v.validateProperty(map, propPath, true);
Assert.assertEquals(3, iv.size()); // null address line 1 + null
// country.name + too long
// country.iso2code
country.setISO2Code("23");
iv = v.validateProperty(map, propPath, true);
Assert.assertEquals(2, iv.size()); // null address line 1 + null
// country.name, country.iso2code
// fixed
Address value = new Address();
value.setCity("whatever");
value.setAddressline1("1 address line");
Set<?> iv2 = v.validateValue(map.getClass(), propPath, value, true);
Assert.assertEquals(1, iv2.size()); // null country
value.setCountry(new Country());
iv2 = v.validateValue(map.getClass(), propPath, value, true);
Assert.assertEquals(1, iv2.size()); // null country.name
value.getCountry().setName("NWO");
iv2 = v.validateValue(map.getClass(), propPath, value, true);
Assert.assertEquals(0, iv2.size());
}
@SuppressWarnings("unchecked")
public void testValidateCascadingKeyedGenericElement() throws InvocationTargetException, NoSuchMethodException,
IllegalAccessException {
final String propPath = "[foo]";
CascadingPropertyValidator v = validator.unwrap(CascadingPropertyValidator.class);
final Address adr = new Address();
Object map = new HashMap<String, Address>();
((Map<String, Address>) map).put("foo", adr);
Country country = new Country();
adr.setCity("dark");
adr.setCountry(country);
Set<?> iv = v.validateProperty(map, propPath);
Assert.assertEquals(1, iv.size()); // null address line 1 (no cascade)
country.setISO2Code("too_long");
iv = v.validateProperty(map, propPath, true);
Assert.assertEquals(3, iv.size()); // null address line 1 + null
// country.name + too long
// country.iso2code
country.setISO2Code("23");
iv = v.validateProperty(map, propPath, true);
Assert.assertEquals(2, iv.size()); // null address line 1 + null
// country.name, country.iso2code
// fixed
Address value = new Address();
value.setCity("whatever");
value.setAddressline1("1 address line");
Set<?> iv2 = v.validateValue(Map.class, propPath, value, true);
Assert.assertEquals(1, iv2.size()); // null country
value.setCountry(new Country());
iv2 = v.validateValue(Map.class, propPath, value, true);
Assert.assertEquals(1, iv2.size()); // null country.name
value.getCountry().setName("NWO");
iv2 = v.validateValue(Map.class, propPath, value, true);
Assert.assertEquals(0, iv2.size());
}
public void testValidateCascadingIndexedElement() throws InvocationTargetException, NoSuchMethodException,
IllegalAccessException {
final String propPath = "[0]";
CascadingPropertyValidator v = validator.unwrap(CascadingPropertyValidator.class);
Address value = new Address();
value.setCity("whatever");
value.setAddressline1("1 address line");
Set<ConstraintViolation<Address[]>> iv;
Address[] array = { value };
iv = v.validateProperty(array, propPath, true);
Assert.assertEquals(1, iv.size()); // null country
value.setCountry(new Country());
iv = v.validateProperty(array, propPath, true);
Assert.assertEquals(1, iv.size()); // null country.name
value.getCountry().setName("NWO");
iv = v.validateProperty(array, propPath, true);
Assert.assertEquals(0, iv.size());
value = new Address();
value.setCity("whatever");
value.setAddressline1("1 address line");
Set<?> iv2;
iv2 = v.validateValue(array.getClass(), propPath, value, true);
Assert.assertEquals(1, iv2.size()); // null country
value.setCountry(new Country());
iv2 = v.validateValue(array.getClass(), propPath, value, true);
Assert.assertEquals(1, iv2.size()); // null country.name
value.getCountry().setName("NWO");
iv2 = v.validateValue(array.getClass(), propPath, value, true);
Assert.assertEquals(0, iv2.size());
}
public void testValidateCascadingIndexedGenericElement() throws InvocationTargetException, NoSuchMethodException,
IllegalAccessException {
final String propPath = "[0]";
CascadingPropertyValidator v = validator.unwrap(CascadingPropertyValidator.class);
Address value = new Address();
value.setCity("whatever");
value.setAddressline1("1 address line");
Set<?> iv;
Object list = Collections.singletonList(value);
iv = v.validateProperty(list, propPath, true);
Assert.assertEquals(1, iv.size()); // null country
value.setCountry(new Country());
iv = v.validateProperty(list, propPath, true);
Assert.assertEquals(1, iv.size()); // null country.name
value.getCountry().setName("NWO");
iv = v.validateProperty(list, propPath, true);
Assert.assertEquals(0, iv.size());
value = new Address();
value.setCity("whatever");
value.setAddressline1("1 address line");
Set<?> iv2;
iv2 = v.validateValue(List.class, propPath, value, true);
Assert.assertEquals(1, iv2.size()); // null country
value.setCountry(new Country());
iv2 = v.validateValue(List.class, propPath, value, true);
Assert.assertEquals(1, iv2.size()); // null country.name
value.getCountry().setName("NWO");
iv2 = v.validateValue(List.class, propPath, value, true);
Assert.assertEquals(0, iv2.size());
}
public interface Foo {
}
public static class FooAddress extends Address {
/**
* {@inheritDoc}
*/
@Override
@NotNull(groups = Foo.class)
public String getCity() {
return super.getCity();
}
}
public void testValidateCascadingPropertyWithMultipleGroupsIgnoresSiblingProperties() {
final String propPath = "addresses[0].country";
CascadingPropertyValidator v = validator.unwrap(CascadingPropertyValidator.class);
Author author = new Author();
author.setAddresses(new ArrayList<Address>());
Address adr = new FooAddress();
author.getAddresses().add(adr);
Country country = new Country();
adr.setCountry(country);
Set<ConstraintViolation<Author>> iv = v.validateProperty(author, propPath, true, Default.class, Foo.class);
Assert.assertEquals(1, iv.size());
}
public void testMetadataAPI() {
BeanDescriptor bookBeanDescriptor = validator.getConstraintsForClass(Book.class);
// expect no constraints on Book's Class-Level
Assert.assertFalse(bookBeanDescriptor.hasConstraints());
// but there are constraints on Book's Property-Level
Assert.assertTrue(bookBeanDescriptor.isBeanConstrained());
Assert.assertTrue(bookBeanDescriptor.getConstraintDescriptors().size() == 0); // no
// constraint
// more specifically "author" and "title"
Assert.assertEquals(4, bookBeanDescriptor.getConstrainedProperties().size());
// not a property
Assert.assertTrue(bookBeanDescriptor.getConstraintsForProperty("doesNotExist") == null);
// property with no constraint
Assert.assertTrue(bookBeanDescriptor.getConstraintsForProperty("description") == null);
PropertyDescriptor propertyDescriptor = bookBeanDescriptor.getConstraintsForProperty("title");
Assert.assertEquals(2, propertyDescriptor.getConstraintDescriptors().size());
Assert.assertTrue("title".equals(propertyDescriptor.getPropertyName()));
// assuming the implementation returns the NotEmpty constraint first
Iterator<ConstraintDescriptor<?>> iter = propertyDescriptor.getConstraintDescriptors().iterator();
ConstraintDescriptor<?> constraintDescriptor = null;
while (iter.hasNext()) {
constraintDescriptor = iter.next();
if (constraintDescriptor.getAnnotation().annotationType().equals(NotNull.class)) {
break;
}
}
Assert.assertTrue(constraintDescriptor != null);
Assert.assertTrue(constraintDescriptor.getGroups().size() == 1); // "first"
Assert.assertEquals(NotNullValidator.class, constraintDescriptor.getConstraintValidatorClasses().get(0));
// assuming the implementation returns the Size constraint first
propertyDescriptor = bookBeanDescriptor.getConstraintsForProperty("subtitle");
Iterator<ConstraintDescriptor<?>> iterator = propertyDescriptor.getConstraintDescriptors().iterator();
constraintDescriptor = iterator.next();
Assert.assertTrue(constraintDescriptor.getAnnotation().annotationType().equals(Size.class));
Assert.assertTrue(((Integer) constraintDescriptor.getAttributes().get("max")) == 30);
Assert.assertTrue(constraintDescriptor.getGroups().size() == 1);
propertyDescriptor = bookBeanDescriptor.getConstraintsForProperty("author");
Assert.assertTrue(propertyDescriptor.getConstraintDescriptors().size() == 1);
Assert.assertTrue(propertyDescriptor.isCascaded());
Assert.assertNull(bookBeanDescriptor.getConstraintsForProperty("unconstraintField"));
}
public void testKeyedMetadata() {
@SuppressWarnings("serial")
BeanDescriptor beanDescriptor = validator.getConstraintsForClass(new HashMap<String, Object>() {
}.getClass());
Assert.assertNotNull(beanDescriptor);
Assert.assertFalse(beanDescriptor.isBeanConstrained());
Assert.assertNull(beanDescriptor.getConstraintsForProperty("[foo]"));
}
public void testGenericKeyedMetadata() {
BeanDescriptor beanDescriptor = validator.getConstraintsForClass(Map.class);
Assert.assertNotNull(beanDescriptor);
Assert.assertFalse(beanDescriptor.isBeanConstrained());
Assert.assertNull(beanDescriptor.getConstraintsForProperty("[foo]"));
}
public void testIndexedMetadata() {
BeanDescriptor beanDescriptor = validator.getConstraintsForClass(Array.newInstance(Author.class, 0).getClass());
Assert.assertNotNull(beanDescriptor);
Assert.assertFalse(beanDescriptor.isBeanConstrained());
Assert.assertNull(beanDescriptor.getConstraintsForProperty("[0]"));
}
public void testGenericIndexedMetadata() {
BeanDescriptor beanDescriptor = validator.getConstraintsForClass(List.class);
Assert.assertNotNull(beanDescriptor);
Assert.assertFalse(beanDescriptor.isBeanConstrained());
Assert.assertNull(beanDescriptor.getConstraintsForProperty("[0]"));
}
}