From 57f6668b37af620654d2f8df2a8501b1d81c4b97 Mon Sep 17 00:00:00 2001 From: Rob Bygrave Date: Wed, 2 Feb 2022 21:57:39 +1300 Subject: [PATCH] Support @DbArray of BigDecimal --- .../server/type/ArrayElementConverter.java | 21 ++++++++ .../server/type/ScalarTypeArrayList.java | 4 ++ .../server/type/ScalarTypeArrayListH2.java | 4 ++ .../org/tests/model/array/EArrayBean.java | 11 ++-- .../tests/model/array/TestDbArray_basic.java | 51 +++++++++---------- .../src/test/resources/ebean.properties | 4 +- 6 files changed, 61 insertions(+), 34 deletions(-) diff --git a/ebean-core/src/main/java/io/ebeaninternal/server/type/ArrayElementConverter.java b/ebean-core/src/main/java/io/ebeaninternal/server/type/ArrayElementConverter.java index 372de8c86..9982124af 100644 --- a/ebean-core/src/main/java/io/ebeaninternal/server/type/ArrayElementConverter.java +++ b/ebean-core/src/main/java/io/ebeaninternal/server/type/ArrayElementConverter.java @@ -1,7 +1,9 @@ package io.ebeaninternal.server.type; import io.ebean.core.type.ScalarType; +import io.ebeaninternal.server.core.BasicTypeConverter; +import java.math.BigDecimal; import java.util.UUID; /** @@ -48,6 +50,8 @@ interface ArrayElementConverter { */ ArrayElementConverter DOUBLE = new DoubleConverter(); + ArrayElementConverter BIG_DECIMAL = new BigDecimalConverter(); + class LongConverter implements ArrayElementConverter { @Override @@ -99,6 +103,23 @@ interface ArrayElementConverter { } } + class BigDecimalConverter implements ArrayElementConverter { + + @Override + public BigDecimal fromSerialized(Object rawValue) { + return fromDbArray(rawValue); + } + + @Override + public BigDecimal fromDbArray(Object rawValue) { + if (rawValue instanceof BigDecimal) { + return (BigDecimal) rawValue; + } else { + return BasicTypeConverter.toBigDecimal(rawValue); + } + } + } + /** * String converter (noop based). */ diff --git a/ebean-core/src/main/java/io/ebeaninternal/server/type/ScalarTypeArrayList.java b/ebean-core/src/main/java/io/ebeaninternal/server/type/ScalarTypeArrayList.java index f0b0ad855..fdeef6a30 100644 --- a/ebean-core/src/main/java/io/ebeaninternal/server/type/ScalarTypeArrayList.java +++ b/ebean-core/src/main/java/io/ebeaninternal/server/type/ScalarTypeArrayList.java @@ -13,6 +13,7 @@ import io.ebeaninternal.json.ModifyAwareList; import javax.persistence.PersistenceException; import java.io.IOException; import java.lang.reflect.Type; +import java.math.BigDecimal; import java.sql.SQLException; import java.sql.Types; import java.util.ArrayList; @@ -59,6 +60,9 @@ class ScalarTypeArrayList extends ScalarTypeArrayBase implements ScalarTyp if (valueType.equals(Double.class)) { return cache.computeIfAbsent(key, s -> new ScalarTypeArrayList(nullable, "float", DocPropertyType.DOUBLE, ArrayElementConverter.DOUBLE)); } + if (valueType.equals(BigDecimal.class)) { + return cache.computeIfAbsent(key, s -> new ScalarTypeArrayList(nullable, "decimal", DocPropertyType.DOUBLE, ArrayElementConverter.BIG_DECIMAL)); + } if (valueType.equals(String.class)) { return cache.computeIfAbsent(key, s -> new ScalarTypeArrayList(nullable, "varchar", DocPropertyType.TEXT, ArrayElementConverter.STRING)); } diff --git a/ebean-core/src/main/java/io/ebeaninternal/server/type/ScalarTypeArrayListH2.java b/ebean-core/src/main/java/io/ebeaninternal/server/type/ScalarTypeArrayListH2.java index c9bc3a3f2..6e16fb018 100644 --- a/ebean-core/src/main/java/io/ebeaninternal/server/type/ScalarTypeArrayListH2.java +++ b/ebean-core/src/main/java/io/ebeaninternal/server/type/ScalarTypeArrayListH2.java @@ -5,6 +5,7 @@ import io.ebean.core.type.DocPropertyType; import io.ebean.core.type.ScalarType; import java.lang.reflect.Type; +import java.math.BigDecimal; import java.sql.SQLException; import java.sql.Types; import java.util.HashMap; @@ -50,6 +51,9 @@ final class ScalarTypeArrayListH2 extends ScalarTypeArrayList { if (valueType.equals(Double.class)) { return cache.computeIfAbsent(key, s -> new ScalarTypeArrayListH2(nullable, "float", DocPropertyType.DOUBLE, ArrayElementConverter.DOUBLE)); } + if (valueType.equals(BigDecimal.class)) { + return cache.computeIfAbsent(key, s -> new ScalarTypeArrayListH2(nullable, "float", DocPropertyType.DOUBLE, ArrayElementConverter.BIG_DECIMAL)); + } if (valueType.equals(String.class)) { return cache.computeIfAbsent(key, s -> new ScalarTypeArrayListH2(nullable, "varchar", DocPropertyType.TEXT, ArrayElementConverter.STRING)); } diff --git a/ebean-test/src/test/java/org/tests/model/array/EArrayBean.java b/ebean-test/src/test/java/org/tests/model/array/EArrayBean.java index dfe91a27b..6ff468209 100644 --- a/ebean-test/src/test/java/org/tests/model/array/EArrayBean.java +++ b/ebean-test/src/test/java/org/tests/model/array/EArrayBean.java @@ -8,6 +8,7 @@ import io.ebean.annotation.NotNull; import javax.persistence.Entity; import javax.persistence.Id; import javax.persistence.Version; +import java.math.BigDecimal; import java.util.ArrayList; import java.util.List; import java.util.Set; @@ -38,7 +39,7 @@ public class EArrayBean { List otherIds = new ArrayList<>(); @DbArray - List doubs; + List decimals; @DbArray List statuses; @@ -103,12 +104,12 @@ public class EArrayBean { this.otherIds = otherIds; } - public List getDoubs() { - return doubs; + public List getDecimals() { + return decimals; } - public void setDoubs(List doubs) { - this.doubs = doubs; + public void setDecimals(List decimals) { + this.decimals = decimals; } public List getStatuses() { diff --git a/ebean-test/src/test/java/org/tests/model/array/TestDbArray_basic.java b/ebean-test/src/test/java/org/tests/model/array/TestDbArray_basic.java index 0a4b1a0fb..b4ed554e3 100644 --- a/ebean-test/src/test/java/org/tests/model/array/TestDbArray_basic.java +++ b/ebean-test/src/test/java/org/tests/model/array/TestDbArray_basic.java @@ -7,6 +7,7 @@ import io.ebean.annotation.Platform; import io.ebean.test.LoggedSql; import org.junit.jupiter.api.Test; +import java.math.BigDecimal; import java.sql.SQLException; import java.util.*; @@ -14,7 +15,7 @@ import static org.assertj.core.api.Assertions.assertThat; import static org.junit.jupiter.api.Assertions.assertEquals; import static org.junit.jupiter.api.Assertions.assertNull; -public class TestDbArray_basic extends BaseTestCase { +class TestDbArray_basic extends BaseTestCase { private final EArrayBean bean = new EArrayBean(); @@ -22,7 +23,7 @@ public class TestDbArray_basic extends BaseTestCase { @Test @IgnorePlatform(Platform.HANA) - public void insert() throws SQLException { + void insert() throws SQLException { DB.find(EArrayBean.class).delete(); bean.setName("some stuff"); assertThat(bean.getStatuses()).as("DbArray is auto initialised").isNotNull(); @@ -31,17 +32,16 @@ public class TestDbArray_basic extends BaseTestCase { phNumbers.add("4321"); phNumbers.add("9823"); - - List doubles = new ArrayList<>(); - doubles.add(1.3); - doubles.add(2.4); + List doubles = new ArrayList<>(); + doubles.add(BigDecimal.valueOf(1.3)); + doubles.add(BigDecimal.valueOf(2.4)); bean.getUids().add(UUID.randomUUID()); bean.getUids().add(UUID.randomUUID()); bean.getOtherIds().add(95L); bean.getOtherIds().add(96L); bean.getOtherIds().add(97L); - bean.setDoubs(doubles); + bean.setDecimals(doubles); bean.setStatuses(new ArrayList<>()); bean.getStatuses().add(EArrayBean.Status.ONE); bean.getStatuses().add(EArrayBean.Status.THREE); @@ -118,7 +118,7 @@ public class TestDbArray_basic extends BaseTestCase { } //@Test//(dependsOnMethods = "insert") - public void json_parse_format() { + void json_parse_format() { String asJson = DB.json().toJson(found); assertThat(asJson).contains("\"phoneNumbers\":[\"4321\",\"9823\"]"); @@ -132,7 +132,7 @@ public class TestDbArray_basic extends BaseTestCase { } //@Test//(dependsOnMethods = "insert") - public void update_when_notDirty() { + void update_when_notDirty() { found.setName("jack"); LoggedSql.start(); @@ -144,7 +144,7 @@ public class TestDbArray_basic extends BaseTestCase { } //@Test//(dependsOnMethods = "update_when_notDirty") - public void update_when_dirty() { + void update_when_dirty() { found.getPhoneNumbers().add("9987"); found.getUids().add(UUID.randomUUID()); @@ -158,8 +158,7 @@ public class TestDbArray_basic extends BaseTestCase { @Test @IgnorePlatform(Platform.HANA) - public void insertNulls() { - + void insertNulls() { EArrayBean bean = new EArrayBean(); bean.setName("some nulls"); bean.setPhoneNumbers(null); @@ -171,8 +170,7 @@ public class TestDbArray_basic extends BaseTestCase { @Test @IgnorePlatform(Platform.HANA) - public void insertAll_when_hasNulls() { - + void insertAll_when_hasNulls() { EArrayBean bean = new EArrayBean(); bean.setName("some nulls"); bean.setPhoneNumbers(null); @@ -191,14 +189,14 @@ public class TestDbArray_basic extends BaseTestCase { */ @ForPlatform({Platform.H2, Platform.POSTGRES}) @Test - public void nullItems() { + void nullItems() { EArrayBean bean = new EArrayBean(); bean.setName("null items"); - List doubles = new ArrayList<>(); - doubles.add(1.3); + List doubles = new ArrayList<>(); + doubles.add(BigDecimal.valueOf(1.3)); doubles.add(null); - doubles.add(2.4); + doubles.add(BigDecimal.valueOf(2.4)); bean.getPhoneNumbers().add("111222333"); bean.getPhoneNumbers().add(null); @@ -213,7 +211,7 @@ public class TestDbArray_basic extends BaseTestCase { bean.getUids().add(null); bean.getUids().add(UUID.randomUUID()); - bean.setDoubs(doubles); + bean.setDecimals(doubles); bean.setStatuses(new ArrayList<>()); bean.getStatuses().add(EArrayBean.Status.ONE); @@ -235,7 +233,7 @@ public class TestDbArray_basic extends BaseTestCase { assertThat(found.getPhoneNumbers()).containsExactly("111222333", null, "333222111"); assertThat(found.getOtherIds()).containsExactly(15L, null, 30L, null); assertNull(found.getUids().get(1)); - assertThat(found.getDoubs()).containsExactly(1.3, null, 2.4); + assertThat(found.getDecimals()).contains(new BigDecimal("1.3"), null, new BigDecimal("2.4")); assertThat(found.getStatuses()).containsExactly(EArrayBean.Status.ONE, null, EArrayBean.Status.THREE); assertThat(found.getVcEnums()).containsExactly(VarcharEnum.ONE, null, VarcharEnum.TWO); assertThat(found.getIntEnums()).containsExactly(null, IntEnum.ZERO, null, IntEnum.TWO); @@ -244,8 +242,7 @@ public class TestDbArray_basic extends BaseTestCase { @Test @IgnorePlatform(Platform.HANA) - public void hitCache() { - + void hitCache() { List uids = new ArrayList<>(); uids.add(UUID.randomUUID()); uids.add(UUID.randomUUID()); @@ -272,16 +269,16 @@ public class TestDbArray_basic extends BaseTestCase { @Test @ForPlatform(Platform.POSTGRES) - public void asDto_withArray() { + void asDto_withArray() { DB.find(EArrayBean.class).delete(); bean.setName("array in dto test"); List phNumbers = bean.getPhoneNumbers(); phNumbers.add("4321"); phNumbers.add("9823"); - List doubs = bean.getDoubs(); - doubs.add(1.23); - doubs.add(4.56); + List doubs = bean.getDecimals(); + doubs.add(BigDecimal.valueOf(1.23)); + doubs.add(BigDecimal.valueOf(4.56)); DB.save(bean); // Data is saved correctly @@ -314,7 +311,7 @@ public class TestDbArray_basic extends BaseTestCase { @Test @ForPlatform(Platform.POSTGRES) - public void sqlUpdate_withArray() { + void sqlUpdate_withArray() { DB.find(EArrayBean.class).delete(); bean.setName("array in sql update test"); DB.save(bean); diff --git a/ebean-test/src/test/resources/ebean.properties b/ebean-test/src/test/resources/ebean.properties index 2b8bdfa45..6dbb4633d 100644 --- a/ebean-test/src/test/resources/ebean.properties +++ b/ebean-test/src/test/resources/ebean.properties @@ -158,8 +158,8 @@ datasource.oracle.url=jdbc:oracle:thin:@localhost:1521:XE #ebean.postgres.timestamp=timestamp datasource.pg.username=unit -datasource.pg.password=unit -datasource.pg.url=jdbc:postgresql://127.0.0.1:5432/unit +datasource.pg.password=test +datasource.pg.url=jdbc:postgresql://127.0.0.1:6432/unit #datasource.pg.capturestacktrace=true datasource.pg.maxStackTraceSize=50