diff --git a/spring-data-commons-core/src/main/java/org/springframework/data/util/TypeDiscoverer.java b/spring-data-commons-core/src/main/java/org/springframework/data/util/TypeDiscoverer.java index bd9343d49..538a9284a 100644 --- a/spring-data-commons-core/src/main/java/org/springframework/data/util/TypeDiscoverer.java +++ b/spring-data-commons-core/src/main/java/org/springframework/data/util/TypeDiscoverer.java @@ -1,5 +1,5 @@ /* - * Copyright 2011 the original author or authors. + * Copyright 2011-2012 the original author or authors. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -27,6 +27,7 @@ import java.lang.reflect.Type; import java.lang.reflect.TypeVariable; import java.lang.reflect.WildcardType; import java.util.ArrayList; +import java.util.Collection; import java.util.List; import java.util.Map; import java.util.concurrent.ConcurrentHashMap; @@ -138,9 +139,9 @@ class TypeDiscoverer implements TypeInformation { } /* - * (non-Javadoc) - * @see org.springframework.data.util.TypeInformation#getParameterTypes(java.lang.reflect.Constructor) - */ + * (non-Javadoc) + * @see org.springframework.data.util.TypeInformation#getParameterTypes(java.lang.reflect.Constructor) + */ public List> getParameterTypes(Constructor constructor) { List> result = new ArrayList>(); @@ -153,12 +154,9 @@ class TypeDiscoverer implements TypeInformation { } /* - * (non-Javadoc) - * - * @see - * org.springframework.data.document.mongodb.TypeDiscovererTest.FieldInformation - * #getField(java.lang.String) - */ + * (non-Javadoc) + * @see org.springframework.data.util.TypeInformation#getProperty(java.lang.String) + */ public TypeInformation getProperty(String fieldname) { int separatorIndex = fieldname.indexOf('.'); @@ -228,17 +226,15 @@ class TypeDiscoverer implements TypeInformation { } /* - * (non-Javadoc) - * - * @see - * org.springframework.data.document.mongodb.TypeDiscovererTest.FieldInformation - * #getType() - */ + * (non-Javadoc) + * @see org.springframework.data.util.TypeInformation#getType() + */ public Class getType() { return resolveType(type); } - /* (non-Javadoc) + /* + * (non-Javadoc) * @see org.springframework.data.util.TypeInformation#getActualType() */ public TypeInformation getActualType() { @@ -251,16 +247,18 @@ class TypeDiscoverer implements TypeInformation { } } - /* (non-Javadoc) - * @see org.springframework.data.util.TypeInformation#isMap() - */ + /* + * (non-Javadoc) + * @see org.springframework.data.util.TypeInformation#isMap() + */ public boolean isMap() { return Map.class.isAssignableFrom(getType()); } - /* (non-Javadoc) - * @see org.springframework.data.util.TypeInformation#getMapValueType() - */ + /* + * (non-Javadoc) + * @see org.springframework.data.util.TypeInformation#getMapValueType() + */ public TypeInformation getMapValueType() { if (!isMap()) { @@ -275,21 +273,30 @@ class TypeDiscoverer implements TypeInformation { return arguments == null ? null : createInfo(arguments[index]); } - /* (non-Javadoc) - * @see org.springframework.data.util.TypeInformation#isCollectionLike() - */ + /* + * (non-Javadoc) + * @see org.springframework.data.util.TypeInformation#isCollectionLike() + */ public boolean isCollectionLike() { Class rawType = getType(); - return rawType.isArray() || Iterable.class.isAssignableFrom(rawType); + + if (rawType.isArray() || Iterable.class.equals(rawType)) { + return true; + } + + return Collection.class.isAssignableFrom(rawType); } - /* (non-Javadoc) - * @see org.springframework.data.util.TypeInformation#getComponentType() - */ + /* + * (non-Javadoc) + * @see org.springframework.data.util.TypeInformation#getComponentType() + */ public TypeInformation getComponentType() { - if (!(isMap() || isCollectionLike())) { + Class rawType = getType(); + + if (!(isMap() || isCollectionLike() || Iterable.class.isAssignableFrom(rawType))) { return null; } @@ -298,8 +305,6 @@ class TypeDiscoverer implements TypeInformation { return createInfo(parameterizedType.getActualTypeArguments()[0]); } - Class rawType = getType(); - if (isMap()) { return getTypeArgument(rawType, Map.class, 0); } @@ -326,10 +331,9 @@ class TypeDiscoverer implements TypeInformation { } /* - * (non-Javadoc) - * - * @see java.lang.Object#equals(java.lang.Object) - */ + * (non-Javadoc) + * @see java.lang.Object#equals(java.lang.Object) + */ @Override public boolean equals(Object obj) { if (obj == this) { @@ -353,10 +357,9 @@ class TypeDiscoverer implements TypeInformation { } /* - * (non-Javadoc) - * - * @see java.lang.Object#hashCode() - */ + * (non-Javadoc) + * @see java.lang.Object#hashCode() + */ @Override public int hashCode() { diff --git a/spring-data-commons-core/src/test/java/org/springframework/data/util/TypeDiscovererUnitTests.java b/spring-data-commons-core/src/test/java/org/springframework/data/util/TypeDiscovererUnitTests.java index b45217c1c..9a1eb008f 100644 --- a/spring-data-commons-core/src/test/java/org/springframework/data/util/TypeDiscovererUnitTests.java +++ b/spring-data-commons-core/src/test/java/org/springframework/data/util/TypeDiscovererUnitTests.java @@ -1,5 +1,5 @@ /* - * Copyright 2011 the original author or authors. + * Copyright 2011-2012 the original author or authors. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -134,6 +134,39 @@ public class TypeDiscovererUnitTests { assertThat(discoverer.getMapValueType(), is(nullValue())); } + /** + * @see DATACMNS-167 + */ + @Test + @SuppressWarnings("rawtypes") + public void doesNotConsiderTypeImplementingIterableACollection() { + + TypeDiscoverer discoverer = new TypeDiscoverer(Person.class, null); + TypeInformation reference = ClassTypeInformation.from(Address.class); + + TypeInformation addresses = discoverer.getProperty("addresses"); + assertThat(addresses.isCollectionLike(), is(false)); + assertThat(addresses.getComponentType(), is(reference)); + + TypeInformation adressIterable = discoverer.getProperty("addressIterable"); + assertThat(adressIterable.isCollectionLike(), is(true)); + assertThat(adressIterable.getComponentType(), is(reference)); + } + + class Person { + + Addresses addresses; + Iterable
addressIterable; + } + + abstract class Addresses implements Iterable
{ + + } + + class Address { + + } + class SelfReferencing { Map parent;