diff --git a/demo/pom.xml b/demo/pom.xml index 73685be..23932d9 100644 --- a/demo/pom.xml +++ b/demo/pom.xml @@ -18,19 +18,9 @@ nl.sanderhautvast - contiguous + contiguous-jdbc 1.0-SNAPSHOT - - org.springframework.boot - spring-boot-starter-web - 2.7.12 - - - org.springframework.boot - spring-boot-starter-data-jdbc - 2.7.12 - org.projectlombok lombok @@ -55,7 +45,7 @@ org.springframework.boot spring-boot-maven-plugin - 2.7.10 + 2.7.12 nl.sanderhautvast.contiguous.demo.DemoApplication diff --git a/demo/src/main/java/nl/sanderhautvast/contiguous/demo/repository/CustomerRepository.java b/demo/src/main/java/nl/sanderhautvast/contiguous/demo/repository/CustomerRepository.java index 20a15cb..7354995 100644 --- a/demo/src/main/java/nl/sanderhautvast/contiguous/demo/repository/CustomerRepository.java +++ b/demo/src/main/java/nl/sanderhautvast/contiguous/demo/repository/CustomerRepository.java @@ -3,6 +3,7 @@ package nl.sanderhautvast.contiguous.demo.repository; import lombok.extern.slf4j.Slf4j; import nl.sanderhautvast.contiguous.ContiguousList; +import nl.sanderhautvast.contiguous.JdbcResults; import nl.sanderhautvast.contiguous.demo.model.Customer; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.jdbc.core.JdbcTemplate; @@ -21,20 +22,7 @@ public class CustomerRepository { public ContiguousList getAllCustomers() { return jdbcTemplate.query("select * from customers limit 5", rs -> { - ContiguousList customers = new ContiguousList<>(Customer.class); - while (rs.next()) { - Customer customer = Customer.builder() - .name(rs.getString("name")) - .email(rs.getString("email")) - .streetname(rs.getString("streetname")) - .housenumber(rs.getInt("housenumber")) - .city(rs.getString("city")) - .country(rs.getString("country")) - .build(); - log.info("{}", customer); - customers.add(customer); - } - return customers; + return JdbcResults.toList(rs, Customer.class); }); } } diff --git a/jackson/pom.xml b/jackson/pom.xml index bf681a5..5cd7717 100644 --- a/jackson/pom.xml +++ b/jackson/pom.xml @@ -6,6 +6,7 @@ nl.sanderhautvast contiguous-jackson 1.1 + Using Jackson to convert Contiguous data to JSON 4.0.0 diff --git a/jdbc/pom.xml b/jdbc/pom.xml new file mode 100644 index 0000000..c0efdd4 --- /dev/null +++ b/jdbc/pom.xml @@ -0,0 +1,52 @@ + + + + nl.sanderhautvast + contiguous-jdbc + 1.0-SNAPSHOT + JDBC functions for Contiguous data + + 4.0.0 + + + 11 + 11 + UTF-8 + + + + + nl.sanderhautvast + contiguous + 1.0-SNAPSHOT + + + org.junit.jupiter + junit-jupiter-engine + 5.8.2 + test + + + org.junit.jupiter + junit-jupiter-api + 5.8.2 + test + + + + org.mockito + mockito-junit-jupiter + 5.3.1 + test + + + org.projectlombok + lombok + 1.18.26 + test + + + + \ No newline at end of file diff --git a/jdbc/src/main/java/nl/sanderhautvast/contiguous/JdbcResults.java b/jdbc/src/main/java/nl/sanderhautvast/contiguous/JdbcResults.java new file mode 100644 index 0000000..b6ab681 --- /dev/null +++ b/jdbc/src/main/java/nl/sanderhautvast/contiguous/JdbcResults.java @@ -0,0 +1,80 @@ +package nl.sanderhautvast.contiguous; + +import java.sql.ResultSet; +import java.sql.SQLException; +import java.util.function.Function; + +/** + * Enables the end user to add values from JDBC to a list of results without creating Objects. + * Every property must have a corresponding field in the ResultSet record (table/view/join etc) + * optionally applying a name mapping if they are not equal + *

+ * // what about null values? + * // test test test + */ +public class JdbcResults { + + /** + * Adds the data to an existing CList + * + * @param result the JDBC ResultSet + * @param list The list to add to + * @throws SQLException when db throws error.. + */ + public static void addAll(ResultSet result, ContiguousList list) throws SQLException { + addAll(result, list, Function.identity()); + } + + /** + * Adds the data to an existing CList. + * + * @param result the JDBC ResultSet + * @param list The list to add to + * @param fieldNameMapper maps the name from the element type property to the actual database column name + * @throws SQLException when db throws error.. + */ + public static void addAll(ResultSet result, ContiguousList list, Function fieldNameMapper) throws SQLException { + ContiguousList.SetterIterator setterIterator = list.setterIterator(); + while (result.next()) { + while (setterIterator.hasNext()) { + ContiguousList.Setter next = setterIterator.next(); + String fieldName = next.getFieldName(); + Object fieldValue; + if (fieldName != null) { + fieldValue = result.getObject(fieldNameMapper.apply(fieldName)); + } else { + // assume single Primitive as Contiguous, so just 1 column in the record + fieldValue = result.getObject(1); + } + next.set(fieldValue); + } + setterIterator.nextRecord(); + } + } + + /** + * Same as addAll, but creates a new CList. + * + * @param result The CList + * @param elementType the desired Object type + * @throws SQLException when db throws error.. + */ + public static ContiguousList toList(ResultSet result, Class elementType) throws SQLException { + ContiguousList list = new ContiguousList<>(elementType); + return toList(result, elementType, Function.identity()); + } + + /** + * Same as addAll, but creates a new CList. + * + * @param result The CList + * @param elementType the desired Object type + * @param fieldNameMapper maps the name from the element type property to the actual database column name + * @throws SQLException when db throws error.. + */ + public static ContiguousList toList(ResultSet result, Class elementType, Function fieldNameMapper) throws SQLException { + ContiguousList list = new ContiguousList<>(elementType); + addAll(result, list, fieldNameMapper); + return list; + } +} diff --git a/jdbc/src/test/java/nl/sanderhautvast/contiguous/JdbcResultsTest.java b/jdbc/src/test/java/nl/sanderhautvast/contiguous/JdbcResultsTest.java new file mode 100644 index 0000000..387b845 --- /dev/null +++ b/jdbc/src/test/java/nl/sanderhautvast/contiguous/JdbcResultsTest.java @@ -0,0 +1,71 @@ +package nl.sanderhautvast.contiguous; + +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.api.extension.ExtendWith; +import org.mockito.Mock; +import org.mockito.junit.jupiter.MockitoExtension; + +import java.sql.ResultSet; +import java.sql.SQLException; +import java.util.List; +import java.util.Map; + +import static org.junit.jupiter.api.Assertions.*; +import static org.mockito.Mockito.when; + +@ExtendWith(MockitoExtension.class) +class JdbcResultsTest { + + @Mock + private ResultSet mockResults; + + @Test + public void testListOfString() throws SQLException { + when(mockResults.next()).thenReturn(true, false); + when(mockResults.getObject(1)).thenReturn("Zaphod"); + + List presidents = JdbcResults.toList(mockResults, String.class); + assertFalse(presidents.isEmpty()); + assertEquals(1, presidents.size()); + + String president = presidents.get(0); + assertEquals("Zaphod", president); + + } + + @Test + public void testListOfBean() throws SQLException { + when(mockResults.next()).thenReturn(true, false); + // the shape of the result equals that of the result (name:String, age:int) + when(mockResults.getObject("name")).thenReturn("Zaphod"); + when(mockResults.getObject("age")).thenReturn(42); // coincidence? + + List presidents = JdbcResults.toList(mockResults, President.class); + assertFalse(presidents.isEmpty()); + assertEquals(1, presidents.size()); + + President president = presidents.get(0); + assertEquals("Zaphod", president.getName()); + assertEquals(42, president.getAge()); + } + + @Test + public void testNameMapping() throws SQLException { + when(mockResults.next()).thenReturn(true, false); + when(mockResults.getObject("name")).thenReturn("Trillian"); + when(mockResults.getObject("realName")).thenReturn("Tricia MacMillan"); + + Map nameMapping = Map.of("name", "name", "earthName", "realName"); + List scientists = JdbcResults.toList(mockResults, Scientist.class, nameMapping::get); + + assertFalse(scientists.isEmpty()); + assertEquals(1, scientists.size()); + + Scientist scientist = scientists.get(0); + assertEquals("Trillian", scientist.getName()); + assertEquals("Tricia MacMillan", scientist.getEarthName()); + } + + +} \ No newline at end of file diff --git a/jdbc/src/test/java/nl/sanderhautvast/contiguous/President.java b/jdbc/src/test/java/nl/sanderhautvast/contiguous/President.java new file mode 100644 index 0000000..8bd8484 --- /dev/null +++ b/jdbc/src/test/java/nl/sanderhautvast/contiguous/President.java @@ -0,0 +1,15 @@ +package nl.sanderhautvast.contiguous; + +import lombok.AllArgsConstructor; +import lombok.Data; +import lombok.NoArgsConstructor; + + +@Data +@AllArgsConstructor +@NoArgsConstructor +public class President { + private String name; + + private int age; +} \ No newline at end of file diff --git a/jdbc/src/test/java/nl/sanderhautvast/contiguous/Scientist.java b/jdbc/src/test/java/nl/sanderhautvast/contiguous/Scientist.java new file mode 100644 index 0000000..6626f8e --- /dev/null +++ b/jdbc/src/test/java/nl/sanderhautvast/contiguous/Scientist.java @@ -0,0 +1,13 @@ +package nl.sanderhautvast.contiguous; + +import lombok.AllArgsConstructor; +import lombok.Data; +import lombok.NoArgsConstructor; + +@Data +@AllArgsConstructor +@NoArgsConstructor +public class Scientist { + private String name; + private String earthName; +} diff --git a/lib/pom.xml b/lib/pom.xml index a2968a0..53749de 100644 --- a/lib/pom.xml +++ b/lib/pom.xml @@ -6,7 +6,7 @@ nl.sanderhautvast contiguous - Datastructures with contiguous storage + Datastructures with contiguous storage. Core library with no external dependencies 1.0-SNAPSHOT jar diff --git a/lib/src/main/java/nl/sanderhautvast/contiguous/BigDecimalHandler.java b/lib/src/main/java/nl/sanderhautvast/contiguous/BigDecimalHandler.java index e2a92b8..ecbebd1 100644 --- a/lib/src/main/java/nl/sanderhautvast/contiguous/BigDecimalHandler.java +++ b/lib/src/main/java/nl/sanderhautvast/contiguous/BigDecimalHandler.java @@ -4,8 +4,8 @@ import java.lang.invoke.MethodHandle; import java.math.BigDecimal; class BigDecimalHandler extends BuiltinTypeHandler { - public BigDecimalHandler(MethodHandle getter, MethodHandle setter) { - super(BigDecimal.class, getter, setter); + public BigDecimalHandler(String propertyName, MethodHandle getter, MethodHandle setter) { + super(BigDecimal.class, propertyName, getter, setter); } @Override diff --git a/lib/src/main/java/nl/sanderhautvast/contiguous/BigIntegerHandler.java b/lib/src/main/java/nl/sanderhautvast/contiguous/BigIntegerHandler.java index 09823b8..ba70f41 100644 --- a/lib/src/main/java/nl/sanderhautvast/contiguous/BigIntegerHandler.java +++ b/lib/src/main/java/nl/sanderhautvast/contiguous/BigIntegerHandler.java @@ -4,8 +4,8 @@ import java.lang.invoke.MethodHandle; import java.math.BigInteger; class BigIntegerHandler extends BuiltinTypeHandler { - public BigIntegerHandler(MethodHandle getter, MethodHandle setter) { - super(BigInteger.class, getter, setter); + public BigIntegerHandler(String propertyName, MethodHandle getter, MethodHandle setter) { + super(BigInteger.class, propertyName, getter, setter); } @Override diff --git a/lib/src/main/java/nl/sanderhautvast/contiguous/BuiltinTypeHandler.java b/lib/src/main/java/nl/sanderhautvast/contiguous/BuiltinTypeHandler.java index 95f51a9..a424479 100644 --- a/lib/src/main/java/nl/sanderhautvast/contiguous/BuiltinTypeHandler.java +++ b/lib/src/main/java/nl/sanderhautvast/contiguous/BuiltinTypeHandler.java @@ -12,8 +12,8 @@ import java.lang.invoke.MethodHandle; * ie. when a bean is added or retrieved from the list */ public abstract class BuiltinTypeHandler extends TypeHandler { - public BuiltinTypeHandler(Class type, MethodHandle getter, MethodHandle setter) { - super(type, getter, setter); + public BuiltinTypeHandler(Class type, String name, MethodHandle getter, MethodHandle setter) { + super(type, name, getter, setter); } /** @@ -29,6 +29,10 @@ public abstract class BuiltinTypeHandler extends TypeHandler { store(propertyValue, typedList); } + void storeValue(Object value, ContiguousList contiguousList) { + store((T)value, contiguousList); + } + private T getValue(Object propertyValue) { // I don't trust this if (getter == null) { diff --git a/lib/src/main/java/nl/sanderhautvast/contiguous/ByteHandler.java b/lib/src/main/java/nl/sanderhautvast/contiguous/ByteHandler.java index d578376..1b0cb3d 100644 --- a/lib/src/main/java/nl/sanderhautvast/contiguous/ByteHandler.java +++ b/lib/src/main/java/nl/sanderhautvast/contiguous/ByteHandler.java @@ -7,8 +7,8 @@ import java.lang.invoke.MethodHandle; */ class ByteHandler extends BuiltinTypeHandler { - public ByteHandler(MethodHandle getter, MethodHandle setter) { - super(Byte.class, getter, setter); + public ByteHandler(String propertyName, MethodHandle getter, MethodHandle setter) { + super(Byte.class, propertyName, getter, setter); } @Override diff --git a/lib/src/main/java/nl/sanderhautvast/contiguous/CompoundTypeHandler.java b/lib/src/main/java/nl/sanderhautvast/contiguous/CompoundTypeHandler.java index 5e2fea9..ca7ccc9 100644 --- a/lib/src/main/java/nl/sanderhautvast/contiguous/CompoundTypeHandler.java +++ b/lib/src/main/java/nl/sanderhautvast/contiguous/CompoundTypeHandler.java @@ -8,8 +8,8 @@ class CompoundTypeHandler extends TypeHandler { - CompoundTypeHandler(Class type) { - super(type, null,null); + CompoundTypeHandler(Class type, String propertyName) { + super(type, propertyName, null,null); } diff --git a/lib/src/main/java/nl/sanderhautvast/contiguous/ContiguousList.java b/lib/src/main/java/nl/sanderhautvast/contiguous/ContiguousList.java index 0ab376a..bda42b1 100644 --- a/lib/src/main/java/nl/sanderhautvast/contiguous/ContiguousList.java +++ b/lib/src/main/java/nl/sanderhautvast/contiguous/ContiguousList.java @@ -8,15 +8,17 @@ import java.nio.charset.StandardCharsets; import java.util.*; //notes: -//1. should find out growth factor of arraylist -//2. elementIndices can be arrayList +// should find out growth factor of arraylist +// investigate data array reuse (pooling, SoftReferences etc) + /** * Short for Contiguous Layout List, an Experimental List implementation * Behaves like an ArrayList in that it's resizable and indexed. * The difference is that it uses an efficiently dehydrated version of the object in a cpu cache friendly, contiguous storage in a bytearray, * without object instance overhead. *

- * Only uses reflection api on creation of the list. + * Only uses reflection api on creation of the list (and in the get() method, but the end user should employ value + * iteration rather than element iteration using said get method). * Adding/Retrieving/Deleting depend on VarHandles and are aimed to be O(L) runtime complexity * where L is the nr of attributes to get/set from the objects (recursively).So O(1) for length of the list *

@@ -35,6 +37,11 @@ import java.util.*; * Implements java.util.List but some methods are not (yet) implemented mainly because they don't make much sense * performance-wise, like the indexed add and set methods. They mess with the memory layout. The list is meant to * be appended at the tail. + *

+ * What I think is a potential use case is a simple CRUD application. + * Here it would become possible to skip Object (when reading from the database), + * and directly map the results to JSON. Both writing and reading should ideally be faster + * than doing it the regular way. */ public class ContiguousList extends NotImplementedList implements List { @@ -52,7 +59,8 @@ public class ContiguousList extends NotImplementedList implements List private int currentElementValueIndex; - private int[] elementIndices = new int[10]; + private int[] elementIndices = new int[10]; // avoids autoboxing. Could also use standard ArrayList though + // is there a standard lib IntList?? private int size; @@ -75,7 +83,7 @@ public class ContiguousList extends NotImplementedList implements List if (PropertyHandlerFactory.isKnownType(type)) { this.rootHandler = PropertyHandlerFactory.forType(type); } else { - CompoundTypeHandler compoundType = new CompoundTypeHandler(type); + CompoundTypeHandler compoundType = new CompoundTypeHandler(type, null);//TODO revisit this.rootHandler = compoundType; try { addPropertyHandlersForCompoundType(type, compoundType); @@ -95,11 +103,11 @@ public class ContiguousList extends NotImplementedList implements List MethodHandle setter = lookup.findSetter(type, field.getName(), fieldType); if (PropertyHandlerFactory.isKnownType(fieldType)) { - BuiltinTypeHandler primitiveType = PropertyHandlerFactory.forType(fieldType, getter, setter); + BuiltinTypeHandler primitiveType = PropertyHandlerFactory.forType(fieldType, field.getName(), getter, setter); parentCompoundType.addHandler(field.getName(), primitiveType); } else { - CompoundTypeHandler newParent = new CompoundTypeHandler(fieldType); + CompoundTypeHandler newParent = new CompoundTypeHandler(fieldType, field.getName()); newParent.setGetter(getter); newParent.setSetter(setter); parentCompoundType.addChild(field, newParent); @@ -170,7 +178,7 @@ public class ContiguousList extends NotImplementedList implements List try { if (rootHandler instanceof BuiltinTypeHandler) { Object read = ValueReader.read(data); - return (E) ((BuiltinTypeHandler) rootHandler).transform(read); + return (E) ((BuiltinTypeHandler) rootHandler).cast(read); } // create a new instance of the list element type E newInstance = (E) rootHandler.getType().getDeclaredConstructor().newInstance(); @@ -295,14 +303,74 @@ public class ContiguousList extends NotImplementedList implements List } handler = typeHandlersIterator.next(); - return handler.transform(rawValue); + return handler.cast(rawValue); } } /** - * Returns an {@link Iterator} over the property values of the specified element in the List. + * Allows 'iterating insertion of data'. Returns an iterator of Setter + * Does not work for compound types yet * - * @return + * @return A Reusable iterator + */ + public SetterIterator setterIterator() { + return new SetterIterator(); + } + + public class Setter { + + private final BuiltinTypeHandler currentHandler; + + public Setter(BuiltinTypeHandler currentHandler) { + this.currentHandler = currentHandler; + } + + public String getFieldName() { + return currentHandler.getName(); + } + + public void set(Object fieldValue) { + currentHandler.storeValue(fieldValue, ContiguousList.this); + } + } + + // TODO proper naming + // BTW do we even need this as a class?? + public class SetterIterator implements Iterator { + private final List properties = new ArrayList<>(); + private Iterator currentSetterIterator; + + public SetterIterator() { + List> builtinTypeHandlers = getBuiltinTypeHandlers(); + for (BuiltinTypeHandler builtinTypeHandler : builtinTypeHandlers) { + properties.add(new Setter(builtinTypeHandler)); + } + // what to do with compound? + currentSetterIterator = this.properties.iterator(); + } + + @Override + public boolean hasNext() { + boolean hasNext = currentSetterIterator.hasNext(); + if (!hasNext){ + extend(); // marks the end of an object + } + return hasNext; + } + + @Override + public Setter next() { + return currentSetterIterator.next(); + } + + public void nextRecord() { + currentSetterIterator = properties.iterator(); + } + + } + + /** + * @return an {@link Iterator} over the property values of the specified element in the List. */ public Iterator valueIterator(int index) { //TODO @@ -402,6 +470,12 @@ public class ContiguousList extends NotImplementedList implements List } } + // to be called by framework to force element count + // used by SetterIterator + void extend() { + size += 1; + } + void storeLong(Long value) { if (value == null) { store0(); diff --git a/lib/src/main/java/nl/sanderhautvast/contiguous/DoubleHandler.java b/lib/src/main/java/nl/sanderhautvast/contiguous/DoubleHandler.java index 04b2002..4c26d23 100644 --- a/lib/src/main/java/nl/sanderhautvast/contiguous/DoubleHandler.java +++ b/lib/src/main/java/nl/sanderhautvast/contiguous/DoubleHandler.java @@ -6,8 +6,8 @@ import java.lang.invoke.MethodHandle; * Stores a double value. */ class DoubleHandler extends BuiltinTypeHandler { - public DoubleHandler(MethodHandle getter, MethodHandle setter) { - super(Double.class, getter, setter); + public DoubleHandler(String propertyName, MethodHandle getter, MethodHandle setter) { + super(Double.class, propertyName, getter, setter); } @Override diff --git a/lib/src/main/java/nl/sanderhautvast/contiguous/FloatHandler.java b/lib/src/main/java/nl/sanderhautvast/contiguous/FloatHandler.java index cc0ab38..69067ee 100644 --- a/lib/src/main/java/nl/sanderhautvast/contiguous/FloatHandler.java +++ b/lib/src/main/java/nl/sanderhautvast/contiguous/FloatHandler.java @@ -3,8 +3,8 @@ package nl.sanderhautvast.contiguous; import java.lang.invoke.MethodHandle; class FloatHandler extends BuiltinTypeHandler { - public FloatHandler(MethodHandle getter, MethodHandle setter) { - super(Float.class, getter, setter); + public FloatHandler(String propertyName, MethodHandle getter, MethodHandle setter) { + super(Float.class, propertyName, getter, setter); } @Override diff --git a/lib/src/main/java/nl/sanderhautvast/contiguous/IntegerHandler.java b/lib/src/main/java/nl/sanderhautvast/contiguous/IntegerHandler.java index 996be7f..014e47d 100644 --- a/lib/src/main/java/nl/sanderhautvast/contiguous/IntegerHandler.java +++ b/lib/src/main/java/nl/sanderhautvast/contiguous/IntegerHandler.java @@ -3,8 +3,8 @@ package nl.sanderhautvast.contiguous; import java.lang.invoke.MethodHandle; class IntegerHandler extends BuiltinTypeHandler { - public IntegerHandler(MethodHandle getter, MethodHandle setter) { - super(Integer.class, getter, setter); + public IntegerHandler(String propertyName, MethodHandle getter, MethodHandle setter) { + super(Integer.class, propertyName, getter, setter); } @Override diff --git a/lib/src/main/java/nl/sanderhautvast/contiguous/LongHandler.java b/lib/src/main/java/nl/sanderhautvast/contiguous/LongHandler.java index 69dfaec..81b5556 100644 --- a/lib/src/main/java/nl/sanderhautvast/contiguous/LongHandler.java +++ b/lib/src/main/java/nl/sanderhautvast/contiguous/LongHandler.java @@ -3,8 +3,8 @@ package nl.sanderhautvast.contiguous; import java.lang.invoke.MethodHandle; class LongHandler extends BuiltinTypeHandler { - public LongHandler(MethodHandle getter, MethodHandle setter) { - super(Long.class, getter, setter); + public LongHandler(String propertyName, MethodHandle getter, MethodHandle setter) { + super(Long.class, propertyName, getter, setter); } @Override diff --git a/lib/src/main/java/nl/sanderhautvast/contiguous/PropertyHandlerFactory.java b/lib/src/main/java/nl/sanderhautvast/contiguous/PropertyHandlerFactory.java index c89bed1..2fd96aa 100644 --- a/lib/src/main/java/nl/sanderhautvast/contiguous/PropertyHandlerFactory.java +++ b/lib/src/main/java/nl/sanderhautvast/contiguous/PropertyHandlerFactory.java @@ -41,14 +41,14 @@ final class PropertyHandlerFactory { return TYPE_HANDLERS.containsKey(type); } - public static BuiltinTypeHandler forType(Class type, MethodHandle getter, MethodHandle setter) { + public static BuiltinTypeHandler forType(Class type, String name, MethodHandle getter, MethodHandle setter) { try { Class> appenderClass = TYPE_HANDLERS.get(type); if (appenderClass == null) { throw new IllegalStateException("No Handler for " + type.getName()); } - return (BuiltinTypeHandler) appenderClass.getDeclaredConstructor(MethodHandle.class, MethodHandle.class) - .newInstance(getter, setter); + return (BuiltinTypeHandler) appenderClass.getDeclaredConstructor(String.class, MethodHandle.class, MethodHandle.class) + .newInstance(name, getter, setter); } catch (NoSuchMethodException | InstantiationException | IllegalAccessException | InvocationTargetException e) { throw new IllegalStateException(e); @@ -56,7 +56,7 @@ final class PropertyHandlerFactory { } public static BuiltinTypeHandler forType(Class type) { - return forType(type, null, null); + return forType(type, null, null, null); } /** diff --git a/lib/src/main/java/nl/sanderhautvast/contiguous/ShortHandler.java b/lib/src/main/java/nl/sanderhautvast/contiguous/ShortHandler.java index d128efb..c58dc1e 100644 --- a/lib/src/main/java/nl/sanderhautvast/contiguous/ShortHandler.java +++ b/lib/src/main/java/nl/sanderhautvast/contiguous/ShortHandler.java @@ -3,8 +3,8 @@ package nl.sanderhautvast.contiguous; import java.lang.invoke.MethodHandle; class ShortHandler extends BuiltinTypeHandler { - public ShortHandler(MethodHandle getter, MethodHandle setter) { - super(Short.class, getter, setter); + public ShortHandler(String propertyName, MethodHandle getter, MethodHandle setter) { + super(Short.class, propertyName, getter, setter); } @Override diff --git a/lib/src/main/java/nl/sanderhautvast/contiguous/StringHandler.java b/lib/src/main/java/nl/sanderhautvast/contiguous/StringHandler.java index 3c6550c..0a83ded 100644 --- a/lib/src/main/java/nl/sanderhautvast/contiguous/StringHandler.java +++ b/lib/src/main/java/nl/sanderhautvast/contiguous/StringHandler.java @@ -3,8 +3,8 @@ package nl.sanderhautvast.contiguous; import java.lang.invoke.MethodHandle; class StringHandler extends BuiltinTypeHandler { - public StringHandler(MethodHandle getter, MethodHandle setter) { - super(String.class, getter, setter); + public StringHandler(String propertyName, MethodHandle getter, MethodHandle setter) { + super(String.class, propertyName, getter, setter); } @Override diff --git a/lib/src/main/java/nl/sanderhautvast/contiguous/TypeHandler.java b/lib/src/main/java/nl/sanderhautvast/contiguous/TypeHandler.java index 08a8162..70a9e34 100644 --- a/lib/src/main/java/nl/sanderhautvast/contiguous/TypeHandler.java +++ b/lib/src/main/java/nl/sanderhautvast/contiguous/TypeHandler.java @@ -5,7 +5,6 @@ import java.lang.invoke.MethodHandle; /** * Abstract basertype over handlers for 'primitives' (ie. long, but also Long, * String..=> built-in types) and compound types (your own). - * * Common ancestor primarily to iterator over properties of any type. * The respective functions are completely different though, and we need `instanceof` to check for the * actual type. (Rust enums!) @@ -15,9 +14,11 @@ public abstract class TypeHandler { protected MethodHandle getter; // both can be null, if it's for a known ('primitive') type protected MethodHandle setter; private final Class type; + private final String name; - public TypeHandler(Class type, MethodHandle getter, MethodHandle setter) { + public TypeHandler(Class type, String name, MethodHandle getter, MethodHandle setter) { this.type = type; + this.name = name; this.getter = getter; this.setter = setter; } @@ -42,4 +43,7 @@ public abstract class TypeHandler { return type; } + public String getName() { + return name; + } } diff --git a/pom.xml b/pom.xml index 341903a..321e5f0 100644 --- a/pom.xml +++ b/pom.xml @@ -10,6 +10,7 @@ lib demo + jdbc jackson contiguous