Provide the Transformer with the field's Type rather than it's Class. The Type
contains generic type information which would allow a transformer to do the right thing with a field of, say, type Set<Integer>. If we had unit tests for StringIterable, I'd know that I didn't just break it. I'd also know that it worked in the first place. :)
This commit is contained in:
@@ -20,6 +20,8 @@
|
|||||||
|
|
||||||
package com.samskivert.depot;
|
package com.samskivert.depot;
|
||||||
|
|
||||||
|
import java.lang.reflect.Type;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Transforms a persistent record field into a format that can be read and written by the
|
* Transforms a persistent record field into a format that can be read and written by the
|
||||||
* underlying database. For example, one might transform an enum into a byte, short or integer. Or
|
* underlying database. For example, one might transform an enum into a byte, short or integer. Or
|
||||||
@@ -48,5 +50,5 @@ public interface Transformer<F,T>
|
|||||||
*
|
*
|
||||||
* @return the transformed value, which will be stored in a field of the persistent record.
|
* @return the transformed value, which will be stored in a field of the persistent record.
|
||||||
*/
|
*/
|
||||||
F fromPersistent (Class<?> fieldType, T value);
|
F fromPersistent (Type fieldType, T value);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -20,6 +20,9 @@
|
|||||||
|
|
||||||
package com.samskivert.depot;
|
package com.samskivert.depot;
|
||||||
|
|
||||||
|
import java.lang.reflect.ParameterizedType;
|
||||||
|
import java.lang.reflect.Type;
|
||||||
|
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.Arrays;
|
import java.util.Arrays;
|
||||||
import java.util.Collection;
|
import java.util.Collection;
|
||||||
@@ -65,7 +68,7 @@ public class Transformers
|
|||||||
}
|
}
|
||||||
return buf.toString();
|
return buf.toString();
|
||||||
}
|
}
|
||||||
public String[] fromPersistent (Class<?> ftype, String value) {
|
public String[] fromPersistent (Type ftype, String value) {
|
||||||
String[] values = value.replace("\\\t", "%%ESCTAB%%").split("\t");
|
String[] values = value.replace("\\\t", "%%ESCTAB%%").split("\t");
|
||||||
for (int ii = 0; ii < values.length; ii++) {
|
for (int ii = 0; ii < values.length; ii++) {
|
||||||
values[ii] = values[ii].replace("%%ESCTAB%%", "\t");
|
values[ii] = values[ii].replace("%%ESCTAB%%", "\t");
|
||||||
@@ -85,7 +88,7 @@ public class Transformers
|
|||||||
return StringIterable.toPersistent0(Arrays.asList(value));
|
return StringIterable.toPersistent0(Arrays.asList(value));
|
||||||
}
|
}
|
||||||
|
|
||||||
public String[] fromPersistent (Class<?> ftype, String encoded)
|
public String[] fromPersistent (Type ftype, String encoded)
|
||||||
{
|
{
|
||||||
if (encoded == null) {
|
if (encoded == null) {
|
||||||
return null;
|
return null;
|
||||||
@@ -102,18 +105,20 @@ public class Transformers
|
|||||||
return toPersistent0(value);
|
return toPersistent0(value);
|
||||||
}
|
}
|
||||||
|
|
||||||
public Iterable<String> fromPersistent (Class<?> ftype, String encoded)
|
public Iterable<String> fromPersistent (Type ftype, String encoded)
|
||||||
{
|
{
|
||||||
ArrayList<String> value = fromPersistent0(encoded);
|
ArrayList<String> value = fromPersistent0(encoded);
|
||||||
|
Type fclass = (ftype instanceof ParameterizedType) ?
|
||||||
|
((ParameterizedType)ftype).getRawType() : ftype;
|
||||||
if (value == null ||
|
if (value == null ||
|
||||||
ftype == ArrayList.class || ftype == List.class || ftype == Collection.class ||
|
fclass == ArrayList.class || fclass == List.class ||
|
||||||
ftype == Iterable.class) {
|
fclass == Collection.class || fclass == Iterable.class) {
|
||||||
return value;
|
return value;
|
||||||
}
|
}
|
||||||
if (ftype == LinkedList.class) {
|
if (fclass == LinkedList.class) {
|
||||||
return Lists.newLinkedList(value);
|
return Lists.newLinkedList(value);
|
||||||
}
|
}
|
||||||
if (ftype == HashSet.class || ftype == Set.class) {
|
if (fclass == HashSet.class || fclass == Set.class) {
|
||||||
return Sets.newHashSet(value);
|
return Sets.newHashSet(value);
|
||||||
}
|
}
|
||||||
// else: reflection? See if it's a collection, call the 0-arg constructor, add all
|
// else: reflection? See if it's a collection, call the 0-arg constructor, add all
|
||||||
|
|||||||
@@ -705,7 +705,7 @@ public abstract class FieldMarshaller<T>
|
|||||||
}
|
}
|
||||||
@Override public void writeToObject (Object po, T value)
|
@Override public void writeToObject (Object po, T value)
|
||||||
throws IllegalArgumentException, IllegalAccessException {
|
throws IllegalArgumentException, IllegalAccessException {
|
||||||
_field.set(po, _xformer.fromPersistent(_field.getType(), value));
|
_field.set(po, _xformer.fromPersistent(_field.getGenericType(), value));
|
||||||
}
|
}
|
||||||
@Override public void writeToStatement (PreparedStatement ps, int column, T value)
|
@Override public void writeToStatement (PreparedStatement ps, int column, T value)
|
||||||
throws SQLException {
|
throws SQLException {
|
||||||
|
|||||||
@@ -21,6 +21,7 @@
|
|||||||
package com.samskivert.depot.tests;
|
package com.samskivert.depot.tests;
|
||||||
|
|
||||||
import java.lang.reflect.Field;
|
import java.lang.reflect.Field;
|
||||||
|
import java.lang.reflect.Type;
|
||||||
import java.util.Set;
|
import java.util.Set;
|
||||||
|
|
||||||
import org.junit.Test;
|
import org.junit.Test;
|
||||||
@@ -92,7 +93,7 @@ public class TransformTest extends TestBase
|
|||||||
return value.value;
|
return value.value;
|
||||||
}
|
}
|
||||||
|
|
||||||
public CustomType fromPersistent (Class<?> ftype, String value) {
|
public CustomType fromPersistent (Type ftype, String value) {
|
||||||
return new CustomType(value);
|
return new CustomType(value);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -102,7 +103,7 @@ public class TransformTest extends TestBase
|
|||||||
public Short toPersistent (ShortEnum value) {
|
public Short toPersistent (ShortEnum value) {
|
||||||
return value.toShort();
|
return value.toShort();
|
||||||
}
|
}
|
||||||
public ShortEnum fromPersistent (Class<?> ftype, Short value) {
|
public ShortEnum fromPersistent (Type ftype, Short value) {
|
||||||
@SuppressWarnings("unchecked") Class<Dummy> eclass = (Class<Dummy>)ftype;
|
@SuppressWarnings("unchecked") Class<Dummy> eclass = (Class<Dummy>)ftype;
|
||||||
return fromShort(eclass, value);
|
return fromShort(eclass, value);
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user