Completed custom serializers in PdxMappingSerializer, SGF-125, SGF-90, SGF-127

This commit is contained in:
David Turanski
2012-09-27 18:12:03 -04:00
parent 0020362b6e
commit 4c95b7044c
6 changed files with 134 additions and 25 deletions

View File

@@ -121,8 +121,6 @@ public class MappingPdxSerializer implements PdxSerializer, ApplicationContextAw
*/
@Override
public Object fromData(Class<?> type, final PdxReader reader) {
// TODO: check for custom serializer (PDX)
final GemfirePersistentEntity<?> entity = mappingContext.getPersistentEntity(type);
EntityInstantiator instantiator = instantiators.getInstantiatorFor(entity);
GemfirePropertyValueProvider propertyValueProvider = new GemfirePropertyValueProvider(reader);
@@ -143,9 +141,15 @@ public class MappingPdxSerializer implements PdxSerializer, ApplicationContextAw
if (entity.isConstructorArgument(persistentProperty)) {
return;
}
// TODO: check for custom serializer (Spring Converter - primitives)
Object value = reader.readField(persistentProperty.getName());
PdxSerializer customSerializer = getCustomSerializer(persistentProperty.getType());
Object value = null;
if (customSerializer != null) {
System.out.println("using custom serializer");
value = customSerializer.fromData(persistentProperty.getType(), reader);
} else {
value = reader.readField(persistentProperty.getName());
}
try {
wrapper.setProperty(persistentProperty, value);
}
@@ -166,7 +170,6 @@ public class MappingPdxSerializer implements PdxSerializer, ApplicationContextAw
*/
@Override
public boolean toData(Object value, final PdxWriter writer) {
// TODO: check for custom serializer (PDX)
GemfirePersistentEntity<?> entity = mappingContext.getPersistentEntity(value.getClass());
final BeanWrapper<PersistentEntity<Object, ?>, Object> wrapper = BeanWrapper.create(value, conversionService);
@@ -174,10 +177,15 @@ public class MappingPdxSerializer implements PdxSerializer, ApplicationContextAw
@SuppressWarnings({ "unchecked", "rawtypes" })
@Override
public void doWithPersistentProperty(GemfirePersistentProperty persistentProperty) {
// TODO: check for custom serializer (Spring Converter)
try {
Object propertyValue = wrapper.getProperty(persistentProperty);
writer.writeField(persistentProperty.getName(), propertyValue, (Class) persistentProperty.getType());
PdxSerializer customSerializer = getCustomSerializer(persistentProperty.getType());
if (customSerializer != null) {
customSerializer.toData(propertyValue, writer);
} else {
writer.writeField(persistentProperty.getName(), propertyValue, (Class) persistentProperty.getType());
}
}
catch (Exception e) {
throw new MappingException("Could not write value for property " + persistentProperty.toString(), e);
@@ -193,4 +201,8 @@ public class MappingPdxSerializer implements PdxSerializer, ApplicationContextAw
return true;
}
private PdxSerializer getCustomSerializer(Class<?> clazz) {
return customSerializers == null ? null : customSerializers.get(clazz);
}
}

View File

@@ -122,12 +122,12 @@ when the same cache is used in multiple application context/bean factories insid
]]></xsd:documentation>
</xsd:annotation>
</xsd:attribute>
<xsd:attribute name="pdx-serializer" type="xsd:string"
<xsd:attribute name="pdx-serializer-ref" type="xsd:string"
use="optional">
<xsd:annotation>
<xsd:documentation><![CDATA[
Sets the PDX serializer for the cache. If this serializer is set, it will be consulted to see if it can serialize any
domain classes which are added to the cache in portable data exchange format.
domain classes which are added to the cache in portable data exchange (PDX) format.
]]></xsd:documentation>
</xsd:annotation>
</xsd:attribute>

View File

@@ -18,16 +18,21 @@ package org.springframework.data.gemfire.mapping;
import static org.hamcrest.CoreMatchers.is;
import static org.junit.Assert.assertThat;
import java.io.DataInput;
import java.io.DataOutput;
import java.io.File;
import java.io.FilenameFilter;
import java.io.IOException;
import org.junit.AfterClass;
import org.junit.Before;
import org.junit.BeforeClass;
import org.junit.Test;
import org.springframework.core.convert.support.DefaultConversionService;
import org.springframework.data.gemfire.repository.sample.Address;
import org.springframework.data.gemfire.repository.sample.Person;
import com.gemstone.gemfire.DataSerializable;
import com.gemstone.gemfire.Instantiator;
import com.gemstone.gemfire.cache.Cache;
import com.gemstone.gemfire.cache.CacheFactory;
import com.gemstone.gemfire.cache.DataPolicy;
@@ -41,12 +46,12 @@ import com.gemstone.gemfire.cache.RegionFactory;
*/
public class MappingPdxSerializerIntegrationTest {
Region<Object, Object> region;
static Region<Object, Object> region;
static Cache cache;
@Before
public void setUp() {
@BeforeClass
public static void setUp() {
MappingPdxSerializer serializer = new MappingPdxSerializer(new GemfireMappingContext(),
new DefaultConversionService());
@@ -81,6 +86,29 @@ public class MappingPdxSerializerIntegrationTest {
assertThat(reference.getLastname(), is(person.getLastname()));
assertThat(reference.address, is(person.address));
}
@Test
public void serializeAndDeserializeCorrectlyWithDataSerializable() {
Address address = new Address();
address.zipCode = "01234";
address.city = "London";
PersonWithDataSerializableProperty person = new PersonWithDataSerializableProperty(2L, "Oliver", "Gierke", new DataSerializableProperty("foo"));
person.address = address;
region.put(2L, person);
Object result = region.get(2L);
assertThat(result instanceof PersonWithDataSerializableProperty, is(true));
PersonWithDataSerializableProperty reference = person;
assertThat(reference.getFirstname(), is(person.getFirstname()));
assertThat(reference.getLastname(), is(person.getLastname()));
assertThat(reference.address, is(person.address));
assertThat(reference.dsProperty.getValue(),is("foo"));
}
@AfterClass
public static void tearDown() {
@@ -99,4 +127,57 @@ public class MappingPdxSerializerIntegrationTest {
new File(name).delete();
}
}
@SuppressWarnings("serial")
public static class PersonWithDataSerializableProperty extends Person {
private DataSerializableProperty dsProperty;
public PersonWithDataSerializableProperty(Long id, String firstname,
String lastname, DataSerializableProperty dsProperty) {
super(id, firstname, lastname);
this.dsProperty = dsProperty;
}
public DataSerializableProperty getDataSerializableProperty() {
return this.dsProperty;
}
}
@SuppressWarnings("serial")
public static class DataSerializableProperty implements DataSerializable {
static {
Instantiator.register(new Instantiator(DataSerializableProperty.class,101) {
public DataSerializable newInstance() {
return new DataSerializableProperty("");
}
});
}
private String value;
public DataSerializableProperty(String value) {
this.value = value;
}
@Override
public void fromData(DataInput dataInput) throws IOException,
ClassNotFoundException {
value = dataInput.readUTF();
}
@Override
public void toData(DataOutput dataOutput) throws IOException {
dataOutput.writeUTF(value);
}
public String getValue() {
return this.value;
}
}
}

View File

@@ -29,10 +29,12 @@ import org.mockito.runners.MockitoJUnitRunner;
import org.springframework.core.convert.ConversionService;
import org.springframework.core.convert.support.GenericConversionService;
import org.springframework.data.convert.EntityInstantiator;
import org.springframework.data.gemfire.repository.sample.Address;
import org.springframework.data.gemfire.repository.sample.Person;
import org.springframework.data.mapping.model.ParameterValueProvider;
import com.gemstone.gemfire.pdx.PdxReader;
import com.gemstone.gemfire.pdx.PdxSerializer;
/**
* Unit tests for {@link MappingPdxSerializer}.
@@ -50,6 +52,9 @@ public class MappingPdxSerializerUnitTests {
EntityInstantiator instantiator;
@Mock
PdxReader reader;
@Mock
PdxSerializer addressSerializer;
@Before
public void setUp() {
@@ -57,14 +62,21 @@ public class MappingPdxSerializerUnitTests {
context = new GemfireMappingContext();
conversionService = new GenericConversionService();
serializer = new MappingPdxSerializer(context, conversionService);
Map<Class<?>,PdxSerializer> customSerializers = new HashMap<Class<?>, PdxSerializer>();
customSerializers.put(Address.class, addressSerializer);
serializer.setCustomSerializers(customSerializers);
}
@Test
@SuppressWarnings("unchecked")
public void usesRegisteredInstantiator() {
Address address = new Address();
address.zipCode = "01234";
address.city = "London";
Person person = new Person(1L, "Oliver", "Gierke");
person.address = address;
ParameterValueProvider<GemfirePersistentProperty> provider = any(ParameterValueProvider.class);
GemfirePersistentEntity<?> entity = any(GemfirePersistentEntity.class);
when(instantiator.createInstance(entity, provider)).thenReturn(person);
@@ -77,5 +89,6 @@ public class MappingPdxSerializerUnitTests {
verify(instantiator, times(1)).createInstance(eq(context.getPersistentEntity(Person.class)),
any(ParameterValueProvider.class));
verify(addressSerializer,times(1)).fromData(eq(Address.class), any(PdxReader.class));
}
}