diff --git a/hibernate-core/src/main/java/org/hibernate/property/access/internal/PropertyAccessStrategyMapImpl.java b/hibernate-core/src/main/java/org/hibernate/property/access/internal/PropertyAccessStrategyMapImpl.java index 562df0e3d05a..539e26a0fc55 100644 --- a/hibernate-core/src/main/java/org/hibernate/property/access/internal/PropertyAccessStrategyMapImpl.java +++ b/hibernate-core/src/main/java/org/hibernate/property/access/internal/PropertyAccessStrategyMapImpl.java @@ -6,6 +6,7 @@ */ package org.hibernate.property.access.internal; +import org.hibernate.mapping.Map; import org.hibernate.property.access.spi.PropertyAccess; import org.hibernate.property.access.spi.PropertyAccessStrategy; @@ -21,6 +22,19 @@ public class PropertyAccessStrategyMapImpl implements PropertyAccessStrategy { @Override public PropertyAccess buildPropertyAccess(Class containerJavaType, String propertyName) { + + // Sometimes containerJavaType is null, but if it isn't, make sure it's a Map. + if (containerJavaType != null && !Map.class.isAssignableFrom(containerJavaType)) { + throw new IllegalArgumentException( + String.format( + "Expecting class: [%1$s], but containerJavaType is of type: [%2$s] for propertyName: [%3$s]", + Map.class.getName(), + containerJavaType.getName(), + propertyName + ) + ); + } + return new PropertyAccessMapImpl( this, propertyName ); } } diff --git a/hibernate-core/src/test/java/org/hibernate/property/PropertyAccessStrategyMapTest.java b/hibernate-core/src/test/java/org/hibernate/property/PropertyAccessStrategyMapTest.java new file mode 100644 index 000000000000..1571ba547163 --- /dev/null +++ b/hibernate-core/src/test/java/org/hibernate/property/PropertyAccessStrategyMapTest.java @@ -0,0 +1,65 @@ +/* + * Hibernate, Relational Persistence for Idiomatic Java + * + * License: GNU Lesser General Public License (LGPL), version 2.1 or later. + * See the lgpl.txt file in the root directory or . + */ +package org.hibernate.property; + +import java.util.Date; +import java.util.HashMap; + +import org.hibernate.mapping.Map; +import org.hibernate.property.access.internal.PropertyAccessStrategyMapImpl; +import org.hibernate.property.access.spi.PropertyAccess; + +import org.hibernate.testing.junit4.BaseUnitTestCase; +import org.junit.Test; + +import static org.junit.Assert.assertEquals; +import static org.junit.Assert.fail; + +public class PropertyAccessStrategyMapTest extends BaseUnitTestCase { + + @Test + public void testBasicMapClass() { + testBasic( Map.class ); + } + + @Test + public void testBasicNullClass() { + testBasic( null ); + } + + @Test + public void testNonMap() { + final PropertyAccessStrategyMapImpl accessStrategy = PropertyAccessStrategyMapImpl.INSTANCE; + + try { + accessStrategy.buildPropertyAccess( Date.class, "time" ); + + fail("Should throw IllegalArgumentException"); + } + catch (IllegalArgumentException e) { + assertEquals( + "Expecting class: [org.hibernate.mapping.Map], but containerJavaType is of type: [java.util.Date] for propertyName: [time]", + e.getMessage() + ); + } + } + + private void testBasic(final Class clazz) { + + final String key = "testKey"; + final String value = "testValue"; + + final PropertyAccessStrategyMapImpl accessStrategy = PropertyAccessStrategyMapImpl.INSTANCE; + final PropertyAccess access = accessStrategy.buildPropertyAccess( clazz, key ); + + final HashMap map = new HashMap<>(); + + access.getSetter().set( map, value, null ); + assertEquals( value, map.get( key ) ); + assertEquals( value, access.getGetter().get( map ) ); + } +}