From ba4bb005bc78447315a3751eb96a435137ced621 Mon Sep 17 00:00:00 2001 From: James Agnew Date: Sat, 13 Jul 2019 17:22:43 -0400 Subject: [PATCH] Switch JPA unit tests to use H2 (#1381) * Start working on this * Ongoing fixes to H2 branch * Work on fixing tests * Updated fixes * Some test fixes * More work on H2 migration * Fixes to try and get the H2 migration building * Test seem to be passing! * Tweaks to locale randomization * Add changelog --- .../main/java/ca/uhn/fhir/util/TestUtil.java | 17 ++- hapi-fhir-jpaserver-base/pom.xml | 6 + .../config/HapiFhirHibernateJpaDialect.java | 14 +-- .../jpa/entity/ResourceReindexJobEntity.java | 12 +- .../reindex/ResourceReindexingSvcImpl.java | 3 +- .../uhn/fhir/jpa/config/TestDstu2Config.java | 7 +- .../uhn/fhir/jpa/config/TestDstu3Config.java | 7 +- .../config/TestDstu3WithoutLuceneConfig.java | 3 +- .../ca/uhn/fhir/jpa/config/TestR4Config.java | 13 +- .../jpa/config/TestR4WithoutLuceneConfig.java | 3 +- .../java/ca/uhn/fhir/jpa/dao/BaseJpaTest.java | 1 + .../FhirResourceDaoDstu2SearchNoFtTest.java | 9 +- .../dao/dstu2/FhirResourceDaoDstu2Test.java | 113 +++++++++--------- .../FhirResourceDaoDstu3SearchNoFtTest.java | 26 ++-- .../dao/dstu3/FhirResourceDaoDstu3Test.java | 37 +++--- ...ourceDaoR4SearchCustomSearchParamTest.java | 5 +- .../r4/FhirResourceDaoR4SearchNoFtTest.java | 9 +- .../FhirResourceDaoR4SearchOptimizedTest.java | 11 +- .../jpa/dao/r4/FhirResourceDaoR4SortTest.java | 10 +- .../r4/FhirResourceDaoR4TerminologyTest.java | 8 +- .../jpa/dao/r4/FhirResourceDaoR4Test.java | 26 ++-- .../provider/r4/ResourceProviderR4Test.java | 15 ++- .../search/SearchCoordinatorSvcImplTest.java | 3 + .../jpa/model/entity/BaseHasResource.java | 17 ++- .../DefaultProfileValidationSupport.java | 5 +- src/changes/changes.xml | 5 + 26 files changed, 220 insertions(+), 165 deletions(-) diff --git a/hapi-fhir-base/src/main/java/ca/uhn/fhir/util/TestUtil.java b/hapi-fhir-base/src/main/java/ca/uhn/fhir/util/TestUtil.java index 9a9f08aee7d..f50033c9b29 100644 --- a/hapi-fhir-base/src/main/java/ca/uhn/fhir/util/TestUtil.java +++ b/hapi-fhir-base/src/main/java/ca/uhn/fhir/util/TestUtil.java @@ -39,6 +39,11 @@ import static org.apache.commons.lang3.StringUtils.defaultString; public class TestUtil { private static final org.slf4j.Logger ourLog = org.slf4j.LoggerFactory.getLogger(TestUtil.class); + private static boolean ourShouldRandomizeTimezones = true; + + public static void setShouldRandomizeTimezones(boolean theShouldRandomizeTimezones) { + ourShouldRandomizeTimezones = theShouldRandomizeTimezones; + } /** * THIS IS FOR UNIT TESTS ONLY - DO NOT CALL THIS METHOD FROM USER CODE @@ -107,7 +112,7 @@ public class TestUtil { * environment */ public static void randomizeLocale() { - Locale[] availableLocales = {Locale.CANADA, Locale.GERMANY, Locale.TAIWAN}; + Locale[] availableLocales = {Locale.CANADA, Locale.GERMANY, Locale.TAIWAN}; Locale.setDefault(availableLocales[(int) (Math.random() * availableLocales.length)]); ourLog.info("Tests are running in locale: " + Locale.getDefault().getDisplayName()); if (Math.random() < 0.5) { @@ -119,9 +124,13 @@ public class TestUtil { System.setProperty("file.encoding", "UTF-8"); System.setProperty("line.separator", "\n"); } - String availableTimeZones[] = {"GMT+08:00", "GMT-05:00", "GMT+00:00", "GMT+03:30"}; - String timeZone = availableTimeZones[(int) (Math.random() * availableTimeZones.length)]; - TimeZone.setDefault(TimeZone.getTimeZone(timeZone)); + + if (ourShouldRandomizeTimezones) { + String availableTimeZones[] = {"GMT+08:00", "GMT-05:00", "GMT+00:00", "GMT+03:30"}; + String timeZone = availableTimeZones[(int) (Math.random() * availableTimeZones.length)]; + TimeZone.setDefault(TimeZone.getTimeZone(timeZone)); + } + ourLog.info("Tests are using time zone: {}", TimeZone.getDefault().getID()); } diff --git a/hapi-fhir-jpaserver-base/pom.xml b/hapi-fhir-jpaserver-base/pom.xml index 7f94371ca95..8b0236e824d 100644 --- a/hapi-fhir-jpaserver-base/pom.xml +++ b/hapi-fhir-jpaserver-base/pom.xml @@ -253,6 +253,12 @@ derbytools test + + com.h2database + h2 + 1.4.199 + test + org.apache.commons commons-dbcp2 diff --git a/hapi-fhir-jpaserver-base/src/main/java/ca/uhn/fhir/jpa/config/HapiFhirHibernateJpaDialect.java b/hapi-fhir-jpaserver-base/src/main/java/ca/uhn/fhir/jpa/config/HapiFhirHibernateJpaDialect.java index 42433d787f5..fa3dca988d3 100644 --- a/hapi-fhir-jpaserver-base/src/main/java/ca/uhn/fhir/jpa/config/HapiFhirHibernateJpaDialect.java +++ b/hapi-fhir-jpaserver-base/src/main/java/ca/uhn/fhir/jpa/config/HapiFhirHibernateJpaDialect.java @@ -31,13 +31,10 @@ import org.hibernate.exception.ConstraintViolationException; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import org.springframework.dao.DataAccessException; -import org.springframework.dao.OptimisticLockingFailureException; -import org.springframework.orm.ObjectOptimisticLockingFailureException; import org.springframework.orm.jpa.vendor.HibernateJpaDialect; import javax.persistence.PersistenceException; -import static org.apache.commons.lang3.StringUtils.defaultString; import static org.apache.commons.lang3.StringUtils.isNotBlank; public class HapiFhirHibernateJpaDialect extends HibernateJpaDialect { @@ -73,13 +70,16 @@ public class HapiFhirHibernateJpaDialect extends HibernateJpaDialect { if (theException instanceof ConstraintViolationException) { String constraintName = ((ConstraintViolationException) theException).getConstraintName(); - switch (defaultString(constraintName)) { - case ResourceHistoryTable.IDX_RESVER_ID_VER: + if (isNotBlank(constraintName)) { + if (constraintName.contains(ResourceHistoryTable.IDX_RESVER_ID_VER)) { throw new ResourceVersionConflictException(messageToPrepend + myLocalizer.getMessage(HapiFhirHibernateJpaDialect.class, "resourceVersionConstraintFailure")); - case ResourceIndexedCompositeStringUnique.IDX_IDXCMPSTRUNIQ_STRING: + } + if (constraintName.contains(ResourceIndexedCompositeStringUnique.IDX_IDXCMPSTRUNIQ_STRING)) { throw new ResourceVersionConflictException(messageToPrepend + myLocalizer.getMessage(HapiFhirHibernateJpaDialect.class, "resourceIndexedCompositeStringUniqueConstraintFailure")); - case ForcedId.IDX_FORCEDID_TYPE_FID: + } + if (constraintName.contains(ForcedId.IDX_FORCEDID_TYPE_FID)) { throw new ResourceVersionConflictException(messageToPrepend + myLocalizer.getMessage(HapiFhirHibernateJpaDialect.class, "forcedIdConstraintFailure")); + } } } diff --git a/hapi-fhir-jpaserver-base/src/main/java/ca/uhn/fhir/jpa/entity/ResourceReindexJobEntity.java b/hapi-fhir-jpaserver-base/src/main/java/ca/uhn/fhir/jpa/entity/ResourceReindexJobEntity.java index 1892e86bb14..2dc0fc60904 100644 --- a/hapi-fhir-jpaserver-base/src/main/java/ca/uhn/fhir/jpa/entity/ResourceReindexJobEntity.java +++ b/hapi-fhir-jpaserver-base/src/main/java/ca/uhn/fhir/jpa/entity/ResourceReindexJobEntity.java @@ -78,7 +78,11 @@ public class ResourceReindexJobEntity implements Serializable { * Inclusive */ public Date getThresholdLow() { - return myThresholdLow; + Date retVal = myThresholdLow; + if (retVal != null) { + retVal = new Date(retVal.getTime()); + } + return retVal; } /** @@ -100,7 +104,11 @@ public class ResourceReindexJobEntity implements Serializable { * Inclusive */ public Date getThresholdHigh() { - return myThresholdHigh; + Date retVal = myThresholdHigh; + if (retVal != null) { + retVal = new Date(retVal.getTime()); + } + return retVal; } /** diff --git a/hapi-fhir-jpaserver-base/src/main/java/ca/uhn/fhir/jpa/search/reindex/ResourceReindexingSvcImpl.java b/hapi-fhir-jpaserver-base/src/main/java/ca/uhn/fhir/jpa/search/reindex/ResourceReindexingSvcImpl.java index 95563487844..52c9066d234 100644 --- a/hapi-fhir-jpaserver-base/src/main/java/ca/uhn/fhir/jpa/search/reindex/ResourceReindexingSvcImpl.java +++ b/hapi-fhir-jpaserver-base/src/main/java/ca/uhn/fhir/jpa/search/reindex/ResourceReindexingSvcImpl.java @@ -43,6 +43,7 @@ import org.apache.commons.lang3.concurrent.BasicThreadFactory; import org.apache.commons.lang3.time.DateUtils; import org.hibernate.search.util.impl.Executors; import org.hl7.fhir.instance.model.api.IBaseResource; +import org.hl7.fhir.r4.model.InstantType; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import org.springframework.beans.factory.annotation.Autowired; @@ -376,7 +377,7 @@ public class ResourceReindexingSvcImpl implements IResourceReindexingSvc { return null; }); - ourLog.info("Completed pass of reindex JOB[{}] - Indexed {} resources in {} ({} / sec) - Have indexed until: {}", theJob.getId(), count, sw.toString(), sw.formatThroughput(count, TimeUnit.SECONDS), newLow); + ourLog.info("Completed pass of reindex JOB[{}] - Indexed {} resources in {} ({} / sec) - Have indexed until: {}", theJob.getId(), count, sw.toString(), sw.formatThroughput(count, TimeUnit.SECONDS), new InstantType(newLow)); return counter.get(); } diff --git a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/config/TestDstu2Config.java b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/config/TestDstu2Config.java index 5d54be94bf0..abc6c727057 100644 --- a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/config/TestDstu2Config.java +++ b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/config/TestDstu2Config.java @@ -8,6 +8,7 @@ import ca.uhn.fhir.validation.ResultSeverityEnum; import net.ttddyy.dsproxy.listener.ThreadQueryCountHolder; import net.ttddyy.dsproxy.support.ProxyDataSourceBuilder; import org.apache.commons.dbcp2.BasicDataSource; +import org.hibernate.dialect.H2Dialect; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import org.springframework.context.annotation.Bean; @@ -99,8 +100,8 @@ public class TestDstu2Config extends BaseJavaConfigDstu2 { } }; - retVal.setDriver(new org.apache.derby.jdbc.EmbeddedDriver()); - retVal.setUrl("jdbc:derby:memory:myUnitTestDBDstu2;create=true"); + retVal.setDriver(new org.h2.Driver()); + retVal.setUrl("jdbc:h2:mem:testdb_dstu2"); retVal.setMaxWaitMillis(10000); retVal.setUsername(""); retVal.setPassword(""); @@ -139,7 +140,7 @@ public class TestDstu2Config extends BaseJavaConfigDstu2 { extraProperties.put("hibernate.format_sql", "true"); extraProperties.put("hibernate.show_sql", "false"); extraProperties.put("hibernate.hbm2ddl.auto", "update"); - extraProperties.put("hibernate.dialect", "ca.uhn.fhir.jpa.util.DerbyTenSevenHapiFhirDialect"); + extraProperties.put("hibernate.dialect", H2Dialect.class.getName()); extraProperties.put("hibernate.search.model_mapping", LuceneSearchMappingFactory.class.getName()); extraProperties.put("hibernate.search.default.directory_provider", "local-heap"); extraProperties.put("hibernate.search.lucene_version", "LUCENE_CURRENT"); diff --git a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/config/TestDstu3Config.java b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/config/TestDstu3Config.java index f4870631887..87469cab62e 100644 --- a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/config/TestDstu3Config.java +++ b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/config/TestDstu3Config.java @@ -9,6 +9,7 @@ import ca.uhn.fhir.rest.server.interceptor.RequestValidatingInterceptor; import ca.uhn.fhir.validation.ResultSeverityEnum; import net.ttddyy.dsproxy.support.ProxyDataSourceBuilder; import org.apache.commons.dbcp2.BasicDataSource; +import org.hibernate.dialect.H2Dialect; import org.springframework.context.annotation.*; import org.springframework.context.support.PropertySourcesPlaceholderConfigurer; import org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean; @@ -81,8 +82,8 @@ public class TestDstu3Config extends BaseJavaConfigDstu3 { } }; - retVal.setDriver(new org.apache.derby.jdbc.EmbeddedDriver()); - retVal.setUrl("jdbc:derby:memory:myUnitTestDBDstu3;create=true"); + retVal.setDriver(new org.h2.Driver()); + retVal.setUrl("jdbc:h2:mem:testdb_dstu3"); retVal.setMaxWaitMillis(10000); retVal.setUsername(""); retVal.setPassword(""); @@ -138,7 +139,7 @@ public class TestDstu3Config extends BaseJavaConfigDstu3 { extraProperties.put("hibernate.format_sql", "false"); extraProperties.put("hibernate.show_sql", "false"); extraProperties.put("hibernate.hbm2ddl.auto", "update"); - extraProperties.put("hibernate.dialect", "ca.uhn.fhir.jpa.util.DerbyTenSevenHapiFhirDialect"); + extraProperties.put("hibernate.dialect", H2Dialect.class.getName()); extraProperties.put("hibernate.search.model_mapping", LuceneSearchMappingFactory.class.getName()); extraProperties.put("hibernate.search.default.directory_provider", "local-heap"); extraProperties.put("hibernate.search.lucene_version", "LUCENE_CURRENT"); diff --git a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/config/TestDstu3WithoutLuceneConfig.java b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/config/TestDstu3WithoutLuceneConfig.java index d3f66cb21d8..e8170a00138 100644 --- a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/config/TestDstu3WithoutLuceneConfig.java +++ b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/config/TestDstu3WithoutLuceneConfig.java @@ -2,6 +2,7 @@ package ca.uhn.fhir.jpa.config; import java.util.Properties; +import org.hibernate.dialect.H2Dialect; import org.hibernate.jpa.HibernatePersistenceProvider; import org.springframework.beans.factory.annotation.Autowire; import org.springframework.context.annotation.Bean; @@ -37,7 +38,7 @@ public class TestDstu3WithoutLuceneConfig extends TestDstu3Config { extraProperties.put("hibernate.format_sql", "false"); extraProperties.put("hibernate.show_sql", "false"); extraProperties.put("hibernate.hbm2ddl.auto", "update"); - extraProperties.put("hibernate.dialect", "ca.uhn.fhir.jpa.util.DerbyTenSevenHapiFhirDialect"); + extraProperties.put("hibernate.dialect", H2Dialect.class.getName()); extraProperties.put("hibernate.search.autoregister_listeners", "false"); return extraProperties; } diff --git a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/config/TestR4Config.java b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/config/TestR4Config.java index c33c0e8f50b..d7641c2b0f2 100644 --- a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/config/TestR4Config.java +++ b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/config/TestR4Config.java @@ -7,6 +7,7 @@ import ca.uhn.fhir.validation.ResultSeverityEnum; import net.ttddyy.dsproxy.listener.SingleQueryCountHolder; import net.ttddyy.dsproxy.support.ProxyDataSourceBuilder; import org.apache.commons.dbcp2.BasicDataSource; +import org.hibernate.dialect.H2Dialect; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import org.springframework.context.annotation.Import; @@ -16,7 +17,6 @@ import org.springframework.transaction.annotation.EnableTransactionManagement; import javax.sql.DataSource; import java.sql.Connection; -import java.sql.SQLException; import java.util.Properties; import static org.junit.Assert.fail; @@ -53,17 +53,14 @@ public class TestR4Config extends BaseJavaConfigR4 { @Override - public Connection getConnection() throws SQLException { + public Connection getConnection() { ConnectionWrapper retVal; try { retVal = new ConnectionWrapper(super.getConnection()); } catch (Exception e) { ourLog.error("Exceeded maximum wait for connection", e); logGetConnectionStackTrace(); -// if ("true".equals(System.getStringProperty("ci"))) { fail("Exceeded maximum wait for connection: " + e.toString()); -// } -// System.exit(1); retVal = null; } @@ -94,8 +91,8 @@ public class TestR4Config extends BaseJavaConfigR4 { } }; - retVal.setDriver(new org.apache.derby.jdbc.EmbeddedDriver()); - retVal.setUrl("jdbc:derby:memory:myUnitTestDBR4;create=true"); + retVal.setDriver(new org.h2.Driver()); + retVal.setUrl("jdbc:h2:mem:testdb_r4"); retVal.setMaxWaitMillis(10000); retVal.setUsername(""); retVal.setPassword(""); @@ -135,7 +132,7 @@ public class TestR4Config extends BaseJavaConfigR4 { extraProperties.put("hibernate.format_sql", "false"); extraProperties.put("hibernate.show_sql", "false"); extraProperties.put("hibernate.hbm2ddl.auto", "update"); - extraProperties.put("hibernate.dialect", "ca.uhn.fhir.jpa.util.DerbyTenSevenHapiFhirDialect"); + extraProperties.put("hibernate.dialect", H2Dialect.class.getName()); extraProperties.put("hibernate.search.model_mapping", ca.uhn.fhir.jpa.search.LuceneSearchMappingFactory.class.getName()); extraProperties.put("hibernate.search.default.directory_provider", "local-heap"); extraProperties.put("hibernate.search.lucene_version", "LUCENE_CURRENT"); diff --git a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/config/TestR4WithoutLuceneConfig.java b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/config/TestR4WithoutLuceneConfig.java index e21d15fce13..dedb0215b16 100644 --- a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/config/TestR4WithoutLuceneConfig.java +++ b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/config/TestR4WithoutLuceneConfig.java @@ -2,6 +2,7 @@ package ca.uhn.fhir.jpa.config; import java.util.Properties; +import org.hibernate.dialect.H2Dialect; import org.hibernate.jpa.HibernatePersistenceProvider; import org.springframework.beans.factory.annotation.Autowire; import org.springframework.context.annotation.Bean; @@ -38,7 +39,7 @@ public class TestR4WithoutLuceneConfig extends TestR4Config { extraProperties.put("hibernate.format_sql", "false"); extraProperties.put("hibernate.show_sql", "false"); extraProperties.put("hibernate.hbm2ddl.auto", "update"); - extraProperties.put("hibernate.dialect", "ca.uhn.fhir.jpa.util.DerbyTenSevenHapiFhirDialect"); + extraProperties.put("hibernate.dialect", H2Dialect.class.getName()); extraProperties.put("hibernate.search.autoregister_listeners", "false"); return extraProperties; } diff --git a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/BaseJpaTest.java b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/BaseJpaTest.java index 341883ef4d2..ae1bff90c99 100644 --- a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/BaseJpaTest.java +++ b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/BaseJpaTest.java @@ -77,6 +77,7 @@ public abstract class BaseJpaTest { static { System.setProperty(Constants.TEST_SYSTEM_PROP_VALIDATION_RESOURCE_CACHES_MS, "1000"); System.setProperty("test", "true"); + TestUtil.setShouldRandomizeTimezones(false); } @Rule diff --git a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/dstu2/FhirResourceDaoDstu2SearchNoFtTest.java b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/dstu2/FhirResourceDaoDstu2SearchNoFtTest.java index 7b648cba375..364af610675 100644 --- a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/dstu2/FhirResourceDaoDstu2SearchNoFtTest.java +++ b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/dstu2/FhirResourceDaoDstu2SearchNoFtTest.java @@ -750,10 +750,9 @@ public class FhirResourceDaoDstu2SearchNoFtTest extends BaseJpaDstu2Test { public void testSearchLastUpdatedParam() throws InterruptedException { String methodName = "testSearchLastUpdatedParam"; - int sleep = 100; - Thread.sleep(sleep); - DateTimeDt beforeAny = new DateTimeDt(new Date(), TemporalPrecisionEnum.MILLI); + TestUtil.sleepOneClick(); + IIdType id1a; { Patient patient = new Patient(); @@ -769,9 +768,9 @@ public class FhirResourceDaoDstu2SearchNoFtTest extends BaseJpaDstu2Test { id1b = myPatientDao.create(patient, mySrd).getId().toUnqualifiedVersionless(); } - Thread.sleep(1100); + TestUtil.sleepOneClick(); DateTimeDt beforeR2 = new DateTimeDt(new Date(), TemporalPrecisionEnum.MILLI); - Thread.sleep(1100); + TestUtil.sleepOneClick(); IIdType id2; { diff --git a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/dstu2/FhirResourceDaoDstu2Test.java b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/dstu2/FhirResourceDaoDstu2Test.java index c29d465ed3b..de27e598c09 100644 --- a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/dstu2/FhirResourceDaoDstu2Test.java +++ b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/dstu2/FhirResourceDaoDstu2Test.java @@ -1,34 +1,18 @@ package ca.uhn.fhir.jpa.dao.dstu2; -import static org.apache.commons.lang3.StringUtils.defaultString; -import static org.hamcrest.Matchers.*; -import static org.junit.Assert.*; -import static org.mockito.ArgumentMatchers.eq; - -import java.io.IOException; -import java.nio.charset.StandardCharsets; -import java.util.*; - -import ca.uhn.fhir.jpa.searchparam.SearchParamConstants; -import ca.uhn.fhir.jpa.searchparam.SearchParameterMap; -import org.apache.commons.io.IOUtils; -import org.apache.commons.lang3.RandomStringUtils; -import org.hamcrest.Matchers; -import org.hamcrest.core.StringContains; -import org.hl7.fhir.instance.model.api.IBaseResource; -import org.hl7.fhir.instance.model.api.IIdType; -import org.junit.*; -import org.junit.Test; - -import ca.uhn.fhir.jpa.dao.*; +import ca.uhn.fhir.jpa.dao.BaseHapiFhirDao; +import ca.uhn.fhir.jpa.dao.BaseHapiFhirResourceDao; +import ca.uhn.fhir.jpa.dao.DaoConfig; +import ca.uhn.fhir.jpa.dao.FhirResourceDaoDstu2; import ca.uhn.fhir.jpa.dao.dstu3.FhirResourceDaoDstu3Test; import ca.uhn.fhir.jpa.model.entity.ResourceIndexedSearchParamString; import ca.uhn.fhir.jpa.model.entity.TagTypeEnum; +import ca.uhn.fhir.jpa.searchparam.SearchParamConstants; +import ca.uhn.fhir.jpa.searchparam.SearchParameterMap; import ca.uhn.fhir.model.api.*; import ca.uhn.fhir.model.base.composite.BaseCodingDt; import ca.uhn.fhir.model.dstu2.composite.*; import ca.uhn.fhir.model.dstu2.resource.*; -import ca.uhn.fhir.model.dstu2.resource.Bundle; import ca.uhn.fhir.model.dstu2.valueset.*; import ca.uhn.fhir.model.primitive.*; import ca.uhn.fhir.model.valueset.BundleEntrySearchModeEnum; @@ -38,6 +22,21 @@ import ca.uhn.fhir.rest.api.server.IBundleProvider; import ca.uhn.fhir.rest.param.*; import ca.uhn.fhir.rest.server.exceptions.*; import ca.uhn.fhir.util.TestUtil; +import org.apache.commons.io.IOUtils; +import org.apache.commons.lang3.RandomStringUtils; +import org.hamcrest.Matchers; +import org.hamcrest.core.StringContains; +import org.hl7.fhir.instance.model.api.IBaseResource; +import org.hl7.fhir.instance.model.api.IIdType; +import org.junit.*; + +import java.io.IOException; +import java.nio.charset.StandardCharsets; +import java.util.*; + +import static org.apache.commons.lang3.StringUtils.defaultString; +import static org.hamcrest.Matchers.*; +import static org.junit.Assert.*; @SuppressWarnings("unchecked") public class FhirResourceDaoDstu2Test extends BaseJpaDstu2Test { @@ -750,7 +749,7 @@ public class FhirResourceDaoDstu2Test extends BaseJpaDstu2Test { patient.addIdentifier().setSystem("ZZZZZZZ").setValue("ZZZZZZZZZ"); id2b = myPatientDao.update(patient, mySrd).getId(); } - ourLog.info("ID1:{} ID2:{} ID2b:{}", new Object[] { id1, id2, id2b }); + ourLog.info("ID1:{} ID2:{} ID2b:{}", new Object[]{id1, id2, id2b}); SearchParameterMap params = new SearchParameterMap(); params.add(Patient.SP_FAMILY, new StringDt("Tester_testDeleteResource")); @@ -1555,28 +1554,28 @@ public class FhirResourceDaoDstu2Test extends BaseJpaDstu2Test { public void testOrganizationName() { //@formatter:off - String inputStr = - "{" + - " \"resourceType\":\"Organization\",\n" + - " \"extension\":[\n" + - " {\n" + - " \"url\":\"http://fhir.connectinggta.ca/Profile/organization#providerIdPool\",\n" + - " \"valueUri\":\"urn:oid:2.16.840.1.113883.3.239.23.21.1\"\n" + - " }\n" + - " ],\n" + - " \"text\":{\n" + - " \"status\":\"empty\",\n" + - " \"div\":\"
No narrative template available for resource profile: http://fhir.connectinggta.ca/Profile/organization
\"\n" + - " },\n" + - " \"identifier\":[\n" + - " {\n" + - " \"use\":\"official\",\n" + - " \"label\":\"HSP 2.16.840.1.113883.3.239.23.21\",\n" + - " \"system\":\"urn:cgta:hsp_ids\",\n" + - " \"value\":\"urn:oid:2.16.840.1.113883.3.239.23.21\"\n" + - " }\n" + - " ],\n" + - " \"name\":\"Peterborough Regional Health Centre\"\n" + + String inputStr = + "{" + + " \"resourceType\":\"Organization\",\n" + + " \"extension\":[\n" + + " {\n" + + " \"url\":\"http://fhir.connectinggta.ca/Profile/organization#providerIdPool\",\n" + + " \"valueUri\":\"urn:oid:2.16.840.1.113883.3.239.23.21.1\"\n" + + " }\n" + + " ],\n" + + " \"text\":{\n" + + " \"status\":\"empty\",\n" + + " \"div\":\"
No narrative template available for resource profile: http://fhir.connectinggta.ca/Profile/organization
\"\n" + + " },\n" + + " \"identifier\":[\n" + + " {\n" + + " \"use\":\"official\",\n" + + " \"label\":\"HSP 2.16.840.1.113883.3.239.23.21\",\n" + + " \"system\":\"urn:cgta:hsp_ids\",\n" + + " \"value\":\"urn:oid:2.16.840.1.113883.3.239.23.21\"\n" + + " }\n" + + " ],\n" + + " \"name\":\"Peterborough Regional Health Centre\"\n" + "}\n"; //@formatter:on @@ -1631,7 +1630,7 @@ public class FhirResourceDaoDstu2Test extends BaseJpaDstu2Test { dr01.setSubject(new ResourceReferenceDt(patientId01)); IIdType drId01 = myDiagnosticReportDao.create(dr01, mySrd).getId(); - ourLog.info("P1[{}] P2[{}] O1[{}] O2[{}] D1[{}]", new Object[] { patientId01, patientId02, obsId01, obsId02, drId01 }); + ourLog.info("P1[{}] P2[{}] O1[{}] O2[{}] D1[{}]", new Object[]{patientId01, patientId02, obsId01, obsId02, drId01}); List result = toList(myObservationDao.search(new SearchParameterMap().setLoadSynchronous(true).add(Observation.SP_SUBJECT, new ReferenceParam(patientId01.getIdPart())))); assertEquals(1, result.size()); @@ -2183,23 +2182,21 @@ public class FhirResourceDaoDstu2Test extends BaseJpaDstu2Test { pm.setSort(new SortSpec(Patient.SP_BIRTHDATE)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); assertEquals(4, actual.size()); - assertThat(actual, contains(id1, id2, id3, id4)); + assertThat(actual, contains(id4, id1, id2, id3)); pm = new SearchParameterMap(); pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", "testtestSortByDate")); pm.setSort(new SortSpec(Patient.SP_BIRTHDATE).setOrder(SortOrderEnum.ASC)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); assertEquals(4, actual.size()); - assertThat(actual, contains(id1, id2, id3, id4)); + assertThat(actual, contains(id4, id1, id2, id3)); pm = new SearchParameterMap(); pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", "testtestSortByDate")); pm.setSort(new SortSpec(Patient.SP_BIRTHDATE).setOrder(SortOrderEnum.DESC)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); assertEquals(4, actual.size()); - // The first would be better, but JPA doesn't do NULLS LAST -// assertThat(actual, contains(id3, id2, id1, id4)); - assertThat(actual, contains(id4, id3, id2, id1)); + assertThat(actual, contains(id3, id2, id1, id4)); } @@ -2237,21 +2234,21 @@ public class FhirResourceDaoDstu2Test extends BaseJpaDstu2Test { pm.setSort(new SortSpec(BaseResource.SP_RES_ID)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); assertEquals(5, actual.size()); - assertThat(actual, contains(idMethodName, id1, id2, id3, id4)); + assertThat(actual, contains(id1, id2, id3, id4, idMethodName)); pm = new SearchParameterMap(); pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", methodName)); pm.setSort(new SortSpec(BaseResource.SP_RES_ID).setOrder(SortOrderEnum.ASC)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); assertEquals(5, actual.size()); - assertThat(actual, contains(idMethodName, id1, id2, id3, id4)); + assertThat(actual, contains(id1, id2, id3, id4, idMethodName)); pm = new SearchParameterMap(); pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", methodName)); pm.setSort(new SortSpec(BaseResource.SP_RES_ID).setOrder(SortOrderEnum.DESC)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); assertEquals(5, actual.size()); - assertThat(actual, contains(id4, id3, id2, id1, idMethodName)); + assertThat(actual, contains(idMethodName, id4, id3, id2, id1)); } @Test @@ -2477,23 +2474,21 @@ public class FhirResourceDaoDstu2Test extends BaseJpaDstu2Test { pm.setSort(new SortSpec(Patient.SP_FAMILY)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); assertEquals(4, actual.size()); - assertThat(actual, contains(id1, id2, id3, id4)); + assertThat(actual, contains(id4, id1, id2, id3)); pm = new SearchParameterMap(); pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", string)); pm.setSort(new SortSpec(Patient.SP_FAMILY).setOrder(SortOrderEnum.ASC)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); assertEquals(4, actual.size()); - assertThat(actual, contains(id1, id2, id3, id4)); + assertThat(actual, contains(id4, id1, id2, id3)); pm = new SearchParameterMap(); pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", string)); pm.setSort(new SortSpec(Patient.SP_FAMILY).setOrder(SortOrderEnum.DESC)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); assertEquals(4, actual.size()); - // The first would be better, but JPA doesn't do NULLS LAST - // assertThat(actual, contains(id3, id2, id1, id4)); - assertThat(actual, contains(id4, id3, id2, id1)); + assertThat(actual, contains(id3, id2, id1, id4)); } /** diff --git a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/dstu3/FhirResourceDaoDstu3SearchNoFtTest.java b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/dstu3/FhirResourceDaoDstu3SearchNoFtTest.java index 36e8ef2c71a..19431b8cadd 100644 --- a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/dstu3/FhirResourceDaoDstu3SearchNoFtTest.java +++ b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/dstu3/FhirResourceDaoDstu3SearchNoFtTest.java @@ -1138,10 +1138,9 @@ public class FhirResourceDaoDstu3SearchNoFtTest extends BaseJpaDstu3Test { public void testSearchLastUpdatedParam() throws InterruptedException { String methodName = "testSearchLastUpdatedParam"; - int sleep = 100; - Thread.sleep(sleep); - DateTimeType beforeAny = new DateTimeType(new Date(), TemporalPrecisionEnum.MILLI); + TestUtil.sleepOneClick(); + IIdType id1a; { Patient patient = new Patient(); @@ -1157,9 +1156,9 @@ public class FhirResourceDaoDstu3SearchNoFtTest extends BaseJpaDstu3Test { id1b = myPatientDao.create(patient, mySrd).getId().toUnqualifiedVersionless(); } - Thread.sleep(1100); + TestUtil.sleepOneClick(); DateTimeType beforeR2 = new DateTimeType(new Date(), TemporalPrecisionEnum.MILLI); - Thread.sleep(1100); + TestUtil.sleepOneClick(); IIdType id2; { @@ -1220,9 +1219,8 @@ public class FhirResourceDaoDstu3SearchNoFtTest extends BaseJpaDstu3Test { } - @SuppressWarnings("deprecation") @Test - public void testSearchLastUpdatedParamWithComparator() throws InterruptedException { + public void testSearchLastUpdatedParamWithComparator() { IIdType id0; { Patient patient = new Patient(); @@ -3215,12 +3213,12 @@ public class FhirResourceDaoDstu3SearchNoFtTest extends BaseJpaDstu3Test { map = new SearchParameterMap(); map.setSort(new SortSpec("_id", SortOrderEnum.ASC)); ids = toUnqualifiedVersionlessIdValues(myPatientDao.search(map)); - assertThat(ids, contains("Patient/AA", "Patient/AB", id1, id2)); + assertThat(ids, contains(id1, id2, "Patient/AA", "Patient/AB")); } @Test - public void testSortOnLastUpdated() throws Exception { + public void testSortOnLastUpdated() { // Numeric ID Patient p01 = new Patient(); p01.setActive(true); @@ -3371,13 +3369,13 @@ public class FhirResourceDaoDstu3SearchNoFtTest extends BaseJpaDstu3Test { map = new SearchParameterMap(); map.setSort(new SortSpec(Patient.SP_FAMILY, SortOrderEnum.ASC).setChain(new SortSpec(Patient.SP_GIVEN, SortOrderEnum.ASC))); ids = toUnqualifiedVersionlessIds(myPatientDao.search(map)); - assertThat(ids, contains(pid2, pid4, pid5, pid3, pid1)); + assertThat(ids.toString(), ids, contains(pid1, pid2, pid3, pid4, pid5)); assertEquals(5, ids.size()); } @Test - public void testSortOnSparselyPopulatedSearchParameter() throws Exception { + public void testSortOnSparselyPopulatedSearchParameter() { Patient pCA = new Patient(); pCA.setId("CA"); pCA.setActive(false); @@ -3421,19 +3419,19 @@ public class FhirResourceDaoDstu3SearchNoFtTest extends BaseJpaDstu3Test { map.setSort(new SortSpec("gender")); ids = toUnqualifiedVersionlessIdValues(myPatientDao.search(map)); ourLog.info("IDS: {}", ids); - assertThat(ids, containsInAnyOrder("Patient/AA", "Patient/AB", "Patient/BA", "Patient/BB", "Patient/CA")); + assertThat(ids.toString(), ids, containsInAnyOrder("Patient/AA", "Patient/AB", "Patient/BA", "Patient/BB", "Patient/CA")); map = new SearchParameterMap(); map.setSort(new SortSpec("gender").setChain(new SortSpec("family", SortOrderEnum.ASC).setChain(new SortSpec("given", SortOrderEnum.ASC)))); ids = toUnqualifiedVersionlessIdValues(myPatientDao.search(map)); ourLog.info("IDS: {}", ids); - assertThat(ids, contains("Patient/AA", "Patient/AB", "Patient/BA", "Patient/BB", "Patient/CA")); + assertThat(ids.toString(), ids, contains("Patient/CA", "Patient/AA", "Patient/AB", "Patient/BA", "Patient/BB")); map = new SearchParameterMap(); map.add(Patient.SP_ACTIVE, new TokenParam(null, "true")); map.setSort(new SortSpec("family", SortOrderEnum.ASC).setChain(new SortSpec("given", SortOrderEnum.ASC))); ids = toUnqualifiedVersionlessIdValues(myPatientDao.search(map)); - assertThat(ids, contains("Patient/AA", "Patient/AB", "Patient/BA", "Patient/BB")); + assertThat(ids.toString(), ids, contains("Patient/AA", "Patient/AB", "Patient/BA", "Patient/BB")); } private String toStringMultiline(List theResults) { diff --git a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/dstu3/FhirResourceDaoDstu3Test.java b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/dstu3/FhirResourceDaoDstu3Test.java index fab416dff9f..95cb5585a17 100644 --- a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/dstu3/FhirResourceDaoDstu3Test.java +++ b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/dstu3/FhirResourceDaoDstu3Test.java @@ -1,6 +1,9 @@ package ca.uhn.fhir.jpa.dao.dstu3; -import ca.uhn.fhir.jpa.dao.*; +import ca.uhn.fhir.jpa.dao.BaseHapiFhirDao; +import ca.uhn.fhir.jpa.dao.BaseHapiFhirResourceDao; +import ca.uhn.fhir.jpa.dao.DaoConfig; +import ca.uhn.fhir.jpa.dao.IFhirResourceDao; import ca.uhn.fhir.jpa.model.entity.ResourceIndexedSearchParamString; import ca.uhn.fhir.jpa.model.entity.TagTypeEnum; import ca.uhn.fhir.jpa.searchparam.SearchParamConstants; @@ -10,7 +13,9 @@ import ca.uhn.fhir.model.api.ResourceMetadataKeyEnum; import ca.uhn.fhir.model.valueset.BundleEntrySearchModeEnum; import ca.uhn.fhir.model.valueset.BundleEntryTransactionMethodEnum; import ca.uhn.fhir.rest.api.Constants; -import ca.uhn.fhir.rest.api.*; +import ca.uhn.fhir.rest.api.MethodOutcome; +import ca.uhn.fhir.rest.api.SortOrderEnum; +import ca.uhn.fhir.rest.api.SortSpec; import ca.uhn.fhir.rest.api.server.IBundleProvider; import ca.uhn.fhir.rest.param.*; import ca.uhn.fhir.rest.server.exceptions.*; @@ -41,10 +46,8 @@ import org.springframework.transaction.support.TransactionTemplate; import java.util.*; import static org.apache.commons.lang3.StringUtils.defaultString; -import static org.hamcrest.Matchers.contains; import static org.hamcrest.Matchers.*; import static org.junit.Assert.*; -import static org.mockito.ArgumentMatchers.eq; @SuppressWarnings({"unchecked", "deprecation"}) public class FhirResourceDaoDstu3Test extends BaseJpaDstu3Test { @@ -1035,7 +1038,7 @@ public class FhirResourceDaoDstu3Test extends BaseJpaDstu3Test { patient.addIdentifier().setSystem("ZZZZZZZ").setValue("ZZZZZZZZZ"); id2b = myPatientDao.update(patient, mySrd).getId(); } - ourLog.info("ID1:{} ID2:{} ID2b:{}", new Object[] {id1, id2, id2b}); + ourLog.info("ID1:{} ID2:{} ID2b:{}", new Object[]{id1, id2, id2b}); SearchParameterMap params = new SearchParameterMap(); params.setLoadSynchronous(true); @@ -2078,7 +2081,7 @@ public class FhirResourceDaoDstu3Test extends BaseJpaDstu3Test { dr01.setSubject(new Reference(patientId01)); IIdType drId01 = myDiagnosticReportDao.create(dr01, mySrd).getId(); - ourLog.info("P1[{}] P2[{}] O1[{}] O2[{}] D1[{}]", new Object[] {patientId01, patientId02, obsId01, obsId02, drId01}); + ourLog.info("P1[{}] P2[{}] O1[{}] O2[{}] D1[{}]", new Object[]{patientId01, patientId02, obsId01, obsId02, drId01}); List result = toList(myObservationDao.search(new SearchParameterMap(Observation.SP_SUBJECT, new ReferenceParam(patientId01.getIdPart())).setLoadSynchronous(true))); assertEquals(1, result.size()); @@ -2695,23 +2698,21 @@ public class FhirResourceDaoDstu3Test extends BaseJpaDstu3Test { pm.setSort(new SortSpec(Patient.SP_BIRTHDATE)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); assertEquals(4, actual.size()); - assertThat(actual, contains(id1, id2, id3, id4)); + assertThat(actual, contains(id4, id1, id2, id3)); pm = new SearchParameterMap(); pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", "testtestSortByDate")); pm.setSort(new SortSpec(Patient.SP_BIRTHDATE).setOrder(SortOrderEnum.ASC)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); assertEquals(4, actual.size()); - assertThat(actual, contains(id1, id2, id3, id4)); + assertThat(actual, contains(id4, id1, id2, id3)); pm = new SearchParameterMap(); pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", "testtestSortByDate")); pm.setSort(new SortSpec(Patient.SP_BIRTHDATE).setOrder(SortOrderEnum.DESC)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); assertEquals(4, actual.size()); - // The first would be better, but JPA doesn't do NULLS LAST - // assertThat(actual, contains(id3, id2, id1, id4)); - assertThat(actual, contains(id4, id3, id2, id1)); + assertThat(actual, contains(id3, id2, id1, id4)); } @@ -2749,21 +2750,21 @@ public class FhirResourceDaoDstu3Test extends BaseJpaDstu3Test { pm.setSort(new SortSpec(IAnyResource.SP_RES_ID)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); assertEquals(5, actual.size()); - assertThat(actual, contains(idMethodName, id1, id2, id3, id4)); + assertThat(actual.toString(), actual, contains(id1, id2, id3, id4, idMethodName)); pm = new SearchParameterMap(); pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", methodName)); pm.setSort(new SortSpec(IAnyResource.SP_RES_ID).setOrder(SortOrderEnum.ASC)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); assertEquals(5, actual.size()); - assertThat(actual, contains(idMethodName, id1, id2, id3, id4)); + assertThat(actual.toString(), actual, contains(id1, id2, id3, id4, idMethodName)); pm = new SearchParameterMap(); pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", methodName)); pm.setSort(new SortSpec(IAnyResource.SP_RES_ID).setOrder(SortOrderEnum.DESC)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); assertEquals(5, actual.size()); - assertThat(actual, contains(id4, id3, id2, id1, idMethodName)); + assertThat(actual.toString(), actual, contains(idMethodName, id4, id3, id2, id1)); } @Test @@ -2988,23 +2989,21 @@ public class FhirResourceDaoDstu3Test extends BaseJpaDstu3Test { pm.setSort(new SortSpec(Patient.SP_FAMILY)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); assertEquals(4, actual.size()); - assertThat(actual, contains(id1, id2, id3, id4)); + assertThat(actual, contains(id4, id1, id2, id3)); pm = new SearchParameterMap(); pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", string)); pm.setSort(new SortSpec(Patient.SP_FAMILY).setOrder(SortOrderEnum.ASC)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); assertEquals(4, actual.size()); - assertThat(actual, contains(id1, id2, id3, id4)); + assertThat(actual, contains(id4, id1, id2, id3)); pm = new SearchParameterMap(); pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", string)); pm.setSort(new SortSpec(Patient.SP_FAMILY).setOrder(SortOrderEnum.DESC)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); assertEquals(4, actual.size()); - // The first would be better, but JPA doesn't do NULLS LAST - // assertThat(actual, contains(id3, id2, id1, id4)); - assertThat(actual, contains(id4, id3, id2, id1)); + assertThat(actual, contains(id3, id2, id1, id4)); } /** diff --git a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/r4/FhirResourceDaoR4SearchCustomSearchParamTest.java b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/r4/FhirResourceDaoR4SearchCustomSearchParamTest.java index 4b87e0d55e4..f7d01453656 100644 --- a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/r4/FhirResourceDaoR4SearchCustomSearchParamTest.java +++ b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/r4/FhirResourceDaoR4SearchCustomSearchParamTest.java @@ -146,7 +146,10 @@ public class FhirResourceDaoR4SearchCustomSearchParamTest extends BaseJpaR4Test mySearchParameterDao.create(fooSp, mySrd); assertEquals(1, myResourceReindexingSvc.forceReindexingPass()); - assertEquals(1, myResourceReindexingSvc.forceReindexingPass()); + myResourceReindexingSvc.forceReindexingPass(); + myResourceReindexingSvc.forceReindexingPass(); + myResourceReindexingSvc.forceReindexingPass(); + myResourceReindexingSvc.forceReindexingPass(); assertEquals(0, myResourceReindexingSvc.forceReindexingPass()); } diff --git a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/r4/FhirResourceDaoR4SearchNoFtTest.java b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/r4/FhirResourceDaoR4SearchNoFtTest.java index 9e6d89fb382..5b5e1eacec9 100644 --- a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/r4/FhirResourceDaoR4SearchNoFtTest.java +++ b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/r4/FhirResourceDaoR4SearchNoFtTest.java @@ -1597,10 +1597,9 @@ public class FhirResourceDaoR4SearchNoFtTest extends BaseJpaR4Test { public void testSearchLastUpdatedParam() throws InterruptedException { String methodName = "testSearchLastUpdatedParam"; - int sleep = 100; - Thread.sleep(sleep); - DateTimeType beforeAny = new DateTimeType(new Date(), TemporalPrecisionEnum.MILLI); + TestUtil.sleepOneClick(); + IIdType id1a; { Patient patient = new Patient(); @@ -1616,9 +1615,9 @@ public class FhirResourceDaoR4SearchNoFtTest extends BaseJpaR4Test { id1b = myPatientDao.create(patient, mySrd).getId().toUnqualifiedVersionless(); } - Thread.sleep(1100); + TestUtil.sleepOneClick(); DateTimeType beforeR2 = new DateTimeType(new Date(), TemporalPrecisionEnum.MILLI); - Thread.sleep(1100); + TestUtil.sleepOneClick(); IIdType id2; { diff --git a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/r4/FhirResourceDaoR4SearchOptimizedTest.java b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/r4/FhirResourceDaoR4SearchOptimizedTest.java index 9fc95f3bb3f..d82b8c63ce3 100644 --- a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/r4/FhirResourceDaoR4SearchOptimizedTest.java +++ b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/r4/FhirResourceDaoR4SearchOptimizedTest.java @@ -51,6 +51,8 @@ public class FhirResourceDaoR4SearchOptimizedTest extends BaseJpaR4Test { @Before public void before() { mySearchCoordinatorSvcImpl = (SearchCoordinatorSvcImpl) AopProxyUtils.getSingletonTarget(mySearchCoordinatorSvc); + mySearchCoordinatorSvcImpl.setLoadingThrottleForUnitTests(null); + mySearchCoordinatorSvcImpl.setSyncSizeForUnitTests(SearchCoordinatorSvcImpl.DEFAULT_SYNC_SIZE); myCaptureQueriesListener.setCaptureQueryStackTrace(true); } @@ -121,7 +123,7 @@ public class FhirResourceDaoR4SearchOptimizedTest extends BaseJpaR4Test { assertThat(ids, empty()); assertEquals(201, myDatabaseBackedPagingProvider.retrieveResultList(null, uuid).size().intValue()); - // Seach with total expicitly requested + // Seach with total explicitly requested params = new SearchParameterMap(); params.add(Patient.SP_NAME, new StringParam("FAM")); params.setSearchTotalMode(SearchTotalModeEnum.ACCURATE); @@ -133,7 +135,7 @@ public class FhirResourceDaoR4SearchOptimizedTest extends BaseJpaR4Test { assertThat(ids, hasSize(10)); assertEquals(201, myDatabaseBackedPagingProvider.retrieveResultList(null, uuid).size().intValue()); - // Seach with count only + // Search with count only params = new SearchParameterMap(); params.add(Patient.SP_NAME, new StringParam().setMissing(false)); params.setSummaryMode(SummaryEnum.COUNT); @@ -148,7 +150,7 @@ public class FhirResourceDaoR4SearchOptimizedTest extends BaseJpaR4Test { } @Test - public void testFetchTotalAccurateForSlowLoading() { + public void testFetchTotalAccurateForSlowLoading() throws InterruptedException { create200Patients(); mySearchCoordinatorSvcImpl.setLoadingThrottleForUnitTests(25); @@ -171,6 +173,9 @@ public class FhirResourceDaoR4SearchOptimizedTest extends BaseJpaR4Test { assertEquals("Patient/PT00000", ids.get(0)); assertEquals("Patient/PT00004", ids.get(4)); + ids = toUnqualifiedVersionlessIdValues(results, 0, 5000, false); + assertEquals(200, ids.size()); + ourLog.info("** About to make new query for search with UUID: {}", uuid); IBundleProvider search2 = myDatabaseBackedPagingProvider.retrieveResultList(null, uuid); Integer search2Size = search2.size(); diff --git a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/r4/FhirResourceDaoR4SortTest.java b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/r4/FhirResourceDaoR4SortTest.java index fd142e85eb1..4b1b06d0d69 100644 --- a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/r4/FhirResourceDaoR4SortTest.java +++ b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/r4/FhirResourceDaoR4SortTest.java @@ -83,8 +83,12 @@ public class FhirResourceDaoR4SortTest extends BaseJpaR4Test { map = new SearchParameterMap(); map.setSort(new SortSpec("_id", SortOrderEnum.ASC)); ids = toUnqualifiedVersionlessIdValues(myPatientDao.search(map)); - assertThat(ids, contains("Patient/AA", "Patient/AB", id1, id2)); + assertThat(ids, contains(id1, id2, "Patient/AA", "Patient/AB")); + map = new SearchParameterMap(); + map.setSort(new SortSpec("_id", SortOrderEnum.DESC)); + ids = toUnqualifiedVersionlessIdValues(myPatientDao.search(map)); + assertThat(ids, contains("Patient/AB", "Patient/AA", id2, id1)); } @Test @@ -247,7 +251,7 @@ public class FhirResourceDaoR4SortTest extends BaseJpaR4Test { map.setSort(new SortSpec(Patient.SP_FAMILY, SortOrderEnum.ASC).setChain(new SortSpec(Patient.SP_GIVEN, SortOrderEnum.ASC))); ids = toUnqualifiedVersionlessIds(myPatientDao.search(map)); ourLog.info("** Got IDs: {}", ids); - assertThat(ids, contains(pid2, pid4, pid5, pid3, pid1)); + assertThat(ids, contains(pid1, pid2, pid3, pid4, pid5)); assertEquals(5, ids.size()); } @@ -303,7 +307,7 @@ public class FhirResourceDaoR4SortTest extends BaseJpaR4Test { map.setSort(new SortSpec("gender").setChain(new SortSpec("family", SortOrderEnum.ASC).setChain(new SortSpec("given", SortOrderEnum.ASC)))); ids = toUnqualifiedVersionlessIdValues(myPatientDao.search(map)); ourLog.info("IDS: {}", ids); - assertThat(ids, contains("Patient/AA", "Patient/AB", "Patient/BA", "Patient/BB", "Patient/CA")); + assertThat(ids, contains("Patient/CA", "Patient/AA", "Patient/AB", "Patient/BA", "Patient/BB")); map = new SearchParameterMap(); map.add(Patient.SP_ACTIVE, new TokenParam(null, "true")); diff --git a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/r4/FhirResourceDaoR4TerminologyTest.java b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/r4/FhirResourceDaoR4TerminologyTest.java index e362d462251..7cdb50077d2 100644 --- a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/r4/FhirResourceDaoR4TerminologyTest.java +++ b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/r4/FhirResourceDaoR4TerminologyTest.java @@ -27,6 +27,7 @@ import org.junit.*; import org.springframework.beans.factory.annotation.Autowired; import java.util.ArrayList; +import java.util.Date; import java.util.List; import java.util.Set; import java.util.stream.Collectors; @@ -253,12 +254,17 @@ public class FhirResourceDaoR4TerminologyTest extends BaseJpaR4Test { public void testConceptTimestamps() { long start = System.currentTimeMillis() - 10; + runInTransaction(() -> { + List concepts = myTermConceptDao.findAll(); + assertThat(concepts, empty()); + }); + createExternalCsDogs(); runInTransaction(() -> { List concepts = myTermConceptDao.findAll(); for (TermConcept next : concepts) { - assertTrue(next.getUpdated().getTime() > start); + assertTrue(new InstantType(new Date(next.getUpdated().getTime())) + " <= " + new InstantType(new Date(start)), next.getUpdated().getTime() > start); } }); } diff --git a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/r4/FhirResourceDaoR4Test.java b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/r4/FhirResourceDaoR4Test.java index 7c41373e782..acd828bfd33 100644 --- a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/r4/FhirResourceDaoR4Test.java +++ b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/r4/FhirResourceDaoR4Test.java @@ -3031,23 +3031,24 @@ public class FhirResourceDaoR4Test extends BaseJpaR4Test { pm.setSort(new SortSpec(Patient.SP_BIRTHDATE)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); assertEquals(4, actual.size()); - assertThat(actual, contains(id1, id2, id3, id4)); + // Nulls first for H2 + assertThat(actual, contains(id4, id1, id2, id3)); pm = new SearchParameterMap(); pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", "testtestSortByDate")); pm.setSort(new SortSpec(Patient.SP_BIRTHDATE).setOrder(SortOrderEnum.ASC)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); assertEquals(4, actual.size()); - assertThat(actual, contains(id1, id2, id3, id4)); + // Nulls first for H2 + assertThat(actual, contains(id4, id1, id2, id3)); pm = new SearchParameterMap(); pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", "testtestSortByDate")); pm.setSort(new SortSpec(Patient.SP_BIRTHDATE).setOrder(SortOrderEnum.DESC)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); assertEquals(4, actual.size()); - // The first would be better, but JPA doesn't do NULLS LAST - // assertThat(actual, contains(id3, id2, id1, id4)); - assertThat(actual, contains(id4, id3, id2, id1)); + assertThat(actual, contains(id3, id2, id1, id4)); +// assertThat(actual, contains(id4, id3, id2, id1)); } @@ -3119,21 +3120,21 @@ public class FhirResourceDaoR4Test extends BaseJpaR4Test { pm.setSort(new SortSpec(IAnyResource.SP_RES_ID)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); assertEquals(5, actual.size()); - assertThat(actual, contains(idMethodName, id1, id2, id3, id4)); + assertThat(actual, contains(id1, id2, id3, id4, idMethodName)); pm = new SearchParameterMap(); pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", methodName)); pm.setSort(new SortSpec(IAnyResource.SP_RES_ID).setOrder(SortOrderEnum.ASC)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); assertEquals(5, actual.size()); - assertThat(actual, contains(idMethodName, id1, id2, id3, id4)); + assertThat(actual, contains(id1, id2, id3, id4, idMethodName)); pm = new SearchParameterMap(); pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", methodName)); pm.setSort(new SortSpec(IAnyResource.SP_RES_ID).setOrder(SortOrderEnum.DESC)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); assertEquals(5, actual.size()); - assertThat(actual, contains(id4, id3, id2, id1, idMethodName)); + assertThat(actual, contains(idMethodName, id4, id3, id2, id1)); } @Test @@ -3357,23 +3358,22 @@ public class FhirResourceDaoR4Test extends BaseJpaR4Test { pm.setSort(new SortSpec(Patient.SP_FAMILY)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); assertEquals(4, actual.size()); - assertThat(actual, contains(id1, id2, id3, id4)); + assertThat(actual, contains(id4, id1, id2, id3)); pm = new SearchParameterMap(); pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", string)); pm.setSort(new SortSpec(Patient.SP_FAMILY).setOrder(SortOrderEnum.ASC)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); assertEquals(4, actual.size()); - assertThat(actual, contains(id1, id2, id3, id4)); + assertThat(actual, contains(id4, id1, id2, id3)); pm = new SearchParameterMap(); pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", string)); pm.setSort(new SortSpec(Patient.SP_FAMILY).setOrder(SortOrderEnum.DESC)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); assertEquals(4, actual.size()); - // The first would be better, but JPA doesn't do NULLS LAST - // assertThat(actual, contains(id3, id2, id1, id4)); - assertThat(actual, contains(id4, id3, id2, id1)); + assertThat(actual, contains(id3, id2, id1, id4)); +// assertThat(actual, contains(id4, id3, id2, id1)); } /** diff --git a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/provider/r4/ResourceProviderR4Test.java b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/provider/r4/ResourceProviderR4Test.java index 1650ded8d84..3ce1f62e8dd 100644 --- a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/provider/r4/ResourceProviderR4Test.java +++ b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/provider/r4/ResourceProviderR4Test.java @@ -72,6 +72,8 @@ import java.nio.charset.StandardCharsets; import java.util.*; import java.util.stream.Collectors; +import static ca.uhn.fhir.jpa.util.TestUtil.sleepAtLeast; +import static ca.uhn.fhir.jpa.util.TestUtil.sleepOneClick; import static org.apache.commons.lang3.StringUtils.isNotBlank; import static org.hamcrest.Matchers.*; import static org.junit.Assert.*; @@ -525,9 +527,11 @@ public class ResourceProviderR4Test extends BaseResourceProviderR4Test { assertEquals(1, exts.size()); } - private List searchAndReturnUnqualifiedIdValues(String uri) throws IOException { + private List searchAndReturnUnqualifiedIdValues(String theUri) throws IOException { List ids; - HttpGet get = new HttpGet(uri); + HttpGet get = new HttpGet(theUri); + + ourLog.info("About to perform search for: {}", theUri); CloseableHttpResponse response = ourHttpClient.execute(get); try { @@ -2320,12 +2324,13 @@ public class ResourceProviderR4Test extends BaseResourceProviderR4Test { List preDates = Lists.newArrayList(); List ids = Lists.newArrayList(); for (int i = 0; i < 10; i++) { - Thread.sleep(100); + sleepOneClick(); preDates.add(new Date()); - Thread.sleep(100); + sleepOneClick(); patient.setId(id); patient.getName().get(0).getFamilyElement().setValue(methodName + "_i" + i); ids.add(myPatientDao.update(patient, mySrd).getId().toUnqualified().getValue()); + sleepOneClick(); } List idValues; @@ -3976,7 +3981,7 @@ public class ResourceProviderR4Test extends BaseResourceProviderR4Test { Search search1 = newTxTemplate().execute(theStatus -> mySearchEntityDao.findByUuid(uuid1)); Date lastReturned1 = search1.getSearchLastReturned(); - TestUtil.sleepOneClick(); + sleepOneClick(); Bundle result2 = ourClient .search() diff --git a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/search/SearchCoordinatorSvcImplTest.java b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/search/SearchCoordinatorSvcImplTest.java index 9d5f07fa637..4125ce03821 100644 --- a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/search/SearchCoordinatorSvcImplTest.java +++ b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/search/SearchCoordinatorSvcImplTest.java @@ -37,6 +37,7 @@ import org.slf4j.LoggerFactory; import org.springframework.data.domain.PageImpl; import org.springframework.data.domain.Pageable; import org.springframework.transaction.PlatformTransactionManager; +import org.springframework.transaction.TransactionStatus; import javax.persistence.EntityManager; import java.util.*; @@ -100,6 +101,8 @@ public class SearchCoordinatorSvcImplTest { when(myCallingDao.newSearchBuilder()).thenReturn(mySearchBuider); + when(myTxManager.getTransaction(any())).thenReturn(mock(TransactionStatus.class)); + doAnswer(theInvocation -> { PersistedJpaBundleProvider provider = (PersistedJpaBundleProvider) theInvocation.getArguments()[0]; provider.setSearchCoordinatorSvc(mySvc); diff --git a/hapi-fhir-jpaserver-model/src/main/java/ca/uhn/fhir/jpa/model/entity/BaseHasResource.java b/hapi-fhir-jpaserver-model/src/main/java/ca/uhn/fhir/jpa/model/entity/BaseHasResource.java index 67d055ed0eb..e6241d40d5e 100644 --- a/hapi-fhir-jpaserver-model/src/main/java/ca/uhn/fhir/jpa/model/entity/BaseHasResource.java +++ b/hapi-fhir-jpaserver-model/src/main/java/ca/uhn/fhir/jpa/model/entity/BaseHasResource.java @@ -82,14 +82,13 @@ public abstract class BaseHasResource implements IBaseResourceEntity { @Override public Date getDeleted() { - return myDeleted; + return cloneDate(myDeleted); } public void setDeleted(Date theDate) { myDeleted = theDate; } - @Override public FhirVersionEnum getFhirVersion() { return myFhirVersion; @@ -125,7 +124,7 @@ public abstract class BaseHasResource implements IBaseResourceEntity { @Override public InstantDt getPublished() { if (myPublished != null) { - return new InstantDt(myPublished); + return new InstantDt(cloneDate(myPublished)); } else { return null; } @@ -149,7 +148,7 @@ public abstract class BaseHasResource implements IBaseResourceEntity { @Override public InstantDt getUpdated() { - return new InstantDt(myUpdated); + return new InstantDt(cloneDate(myUpdated)); } public void setUpdated(Date theUpdated) { @@ -162,7 +161,7 @@ public abstract class BaseHasResource implements IBaseResourceEntity { @Override public Date getUpdatedDate() { - return myUpdated; + return cloneDate(myUpdated); } @Override @@ -177,4 +176,12 @@ public abstract class BaseHasResource implements IBaseResourceEntity { myHasTags = theHasTags; } + static Date cloneDate(Date theDate) { + Date retVal = theDate; + if (retVal != null) { + retVal = new Date(retVal.getTime()); + } + return retVal; + } + } diff --git a/hapi-fhir-structures-dstu2.1/src/main/java/org/hl7/fhir/dstu2016may/hapi/validation/DefaultProfileValidationSupport.java b/hapi-fhir-structures-dstu2.1/src/main/java/org/hl7/fhir/dstu2016may/hapi/validation/DefaultProfileValidationSupport.java index 68723c53338..facc36d4fa9 100644 --- a/hapi-fhir-structures-dstu2.1/src/main/java/org/hl7/fhir/dstu2016may/hapi/validation/DefaultProfileValidationSupport.java +++ b/hapi-fhir-structures-dstu2.1/src/main/java/org/hl7/fhir/dstu2016may/hapi/validation/DefaultProfileValidationSupport.java @@ -15,6 +15,7 @@ import org.hl7.fhir.utilities.validation.ValidationMessage.IssueSeverity; import java.io.InputStream; import java.io.InputStreamReader; +import java.nio.charset.StandardCharsets; import java.util.*; import static org.apache.commons.lang3.StringUtils.isNotBlank; @@ -161,7 +162,7 @@ public class DefaultProfileValidationSupport implements IValidationSupport { InputStreamReader reader = null; if (inputStream != null) { try { - reader = new InputStreamReader(inputStream, Charsets.UTF_8); + reader = new InputStreamReader(inputStream, StandardCharsets.UTF_8); Bundle bundle = theContext.newXmlParser().parseResource(Bundle.class, reader); for (BundleEntryComponent next : bundle.getEntry()) { @@ -194,7 +195,7 @@ public class DefaultProfileValidationSupport implements IValidationSupport { ourLog.info("Loading structure definitions from classpath: {}", theClasspath); InputStream valuesetText = DefaultProfileValidationSupport.class.getResourceAsStream(theClasspath); if (valuesetText != null) { - InputStreamReader reader = new InputStreamReader(valuesetText, Charsets.UTF_8); + InputStreamReader reader = new InputStreamReader(valuesetText, StandardCharsets.UTF_8); Bundle bundle = theContext.newXmlParser().parseResource(Bundle.class, reader); for (BundleEntryComponent next : bundle.getEntry()) { diff --git a/src/changes/changes.xml b/src/changes/changes.xml index b9f3f45c465..daff7757eeb 100644 --- a/src/changes/changes.xml +++ b/src/changes/changes.xml @@ -270,6 +270,11 @@ The _summary]]> element was not always respected when encoding JSON resources. + + The JPA server now uses the H2 database instead of the derby database to run its + unit tests. We are hoping that this cuts down on the number of false test failures + we get due to mysterious derby failures. + Added a new Pointcut STORAGE_PRESTORAGE_EXPUNGE_EVERYTHING that is called at the start of the expungeEverything operation.