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
This commit is contained in:
James Agnew 2019-07-13 17:22:43 -04:00 committed by GitHub
parent e54af48964
commit ba4bb005bc
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
26 changed files with 220 additions and 165 deletions

View File

@ -39,6 +39,11 @@ import static org.apache.commons.lang3.StringUtils.defaultString;
public class TestUtil { public class TestUtil {
private static final org.slf4j.Logger ourLog = org.slf4j.LoggerFactory.getLogger(TestUtil.class); 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;
}
/** /**
* <b>THIS IS FOR UNIT TESTS ONLY - DO NOT CALL THIS METHOD FROM USER CODE</b> * <b>THIS IS FOR UNIT TESTS ONLY - DO NOT CALL THIS METHOD FROM USER CODE</b>
@ -107,7 +112,7 @@ public class TestUtil {
* environment * environment
*/ */
public static void randomizeLocale() { 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)]); Locale.setDefault(availableLocales[(int) (Math.random() * availableLocales.length)]);
ourLog.info("Tests are running in locale: " + Locale.getDefault().getDisplayName()); ourLog.info("Tests are running in locale: " + Locale.getDefault().getDisplayName());
if (Math.random() < 0.5) { if (Math.random() < 0.5) {
@ -119,9 +124,13 @@ public class TestUtil {
System.setProperty("file.encoding", "UTF-8"); System.setProperty("file.encoding", "UTF-8");
System.setProperty("line.separator", "\n"); 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)]; if (ourShouldRandomizeTimezones) {
TimeZone.setDefault(TimeZone.getTimeZone(timeZone)); 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()); ourLog.info("Tests are using time zone: {}", TimeZone.getDefault().getID());
} }

View File

@ -253,6 +253,12 @@
<artifactId>derbytools</artifactId> <artifactId>derbytools</artifactId>
<scope>test</scope> <scope>test</scope>
</dependency> </dependency>
<dependency>
<groupId>com.h2database</groupId>
<artifactId>h2</artifactId>
<version>1.4.199</version>
<scope>test</scope>
</dependency>
<dependency> <dependency>
<groupId>org.apache.commons</groupId> <groupId>org.apache.commons</groupId>
<artifactId>commons-dbcp2</artifactId> <artifactId>commons-dbcp2</artifactId>

View File

@ -31,13 +31,10 @@ import org.hibernate.exception.ConstraintViolationException;
import org.slf4j.Logger; import org.slf4j.Logger;
import org.slf4j.LoggerFactory; import org.slf4j.LoggerFactory;
import org.springframework.dao.DataAccessException; import org.springframework.dao.DataAccessException;
import org.springframework.dao.OptimisticLockingFailureException;
import org.springframework.orm.ObjectOptimisticLockingFailureException;
import org.springframework.orm.jpa.vendor.HibernateJpaDialect; import org.springframework.orm.jpa.vendor.HibernateJpaDialect;
import javax.persistence.PersistenceException; import javax.persistence.PersistenceException;
import static org.apache.commons.lang3.StringUtils.defaultString;
import static org.apache.commons.lang3.StringUtils.isNotBlank; import static org.apache.commons.lang3.StringUtils.isNotBlank;
public class HapiFhirHibernateJpaDialect extends HibernateJpaDialect { public class HapiFhirHibernateJpaDialect extends HibernateJpaDialect {
@ -73,13 +70,16 @@ public class HapiFhirHibernateJpaDialect extends HibernateJpaDialect {
if (theException instanceof ConstraintViolationException) { if (theException instanceof ConstraintViolationException) {
String constraintName = ((ConstraintViolationException) theException).getConstraintName(); String constraintName = ((ConstraintViolationException) theException).getConstraintName();
switch (defaultString(constraintName)) { if (isNotBlank(constraintName)) {
case ResourceHistoryTable.IDX_RESVER_ID_VER: if (constraintName.contains(ResourceHistoryTable.IDX_RESVER_ID_VER)) {
throw new ResourceVersionConflictException(messageToPrepend + myLocalizer.getMessage(HapiFhirHibernateJpaDialect.class, "resourceVersionConstraintFailure")); 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")); 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")); throw new ResourceVersionConflictException(messageToPrepend + myLocalizer.getMessage(HapiFhirHibernateJpaDialect.class, "forcedIdConstraintFailure"));
}
} }
} }

View File

@ -78,7 +78,11 @@ public class ResourceReindexJobEntity implements Serializable {
* Inclusive * Inclusive
*/ */
public Date getThresholdLow() { 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 * Inclusive
*/ */
public Date getThresholdHigh() { public Date getThresholdHigh() {
return myThresholdHigh; Date retVal = myThresholdHigh;
if (retVal != null) {
retVal = new Date(retVal.getTime());
}
return retVal;
} }
/** /**

View File

@ -43,6 +43,7 @@ import org.apache.commons.lang3.concurrent.BasicThreadFactory;
import org.apache.commons.lang3.time.DateUtils; import org.apache.commons.lang3.time.DateUtils;
import org.hibernate.search.util.impl.Executors; import org.hibernate.search.util.impl.Executors;
import org.hl7.fhir.instance.model.api.IBaseResource; import org.hl7.fhir.instance.model.api.IBaseResource;
import org.hl7.fhir.r4.model.InstantType;
import org.slf4j.Logger; import org.slf4j.Logger;
import org.slf4j.LoggerFactory; import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired; import org.springframework.beans.factory.annotation.Autowired;
@ -376,7 +377,7 @@ public class ResourceReindexingSvcImpl implements IResourceReindexingSvc {
return null; 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(); return counter.get();
} }

View File

@ -8,6 +8,7 @@ import ca.uhn.fhir.validation.ResultSeverityEnum;
import net.ttddyy.dsproxy.listener.ThreadQueryCountHolder; import net.ttddyy.dsproxy.listener.ThreadQueryCountHolder;
import net.ttddyy.dsproxy.support.ProxyDataSourceBuilder; import net.ttddyy.dsproxy.support.ProxyDataSourceBuilder;
import org.apache.commons.dbcp2.BasicDataSource; import org.apache.commons.dbcp2.BasicDataSource;
import org.hibernate.dialect.H2Dialect;
import org.slf4j.Logger; import org.slf4j.Logger;
import org.slf4j.LoggerFactory; import org.slf4j.LoggerFactory;
import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Bean;
@ -99,8 +100,8 @@ public class TestDstu2Config extends BaseJavaConfigDstu2 {
} }
}; };
retVal.setDriver(new org.apache.derby.jdbc.EmbeddedDriver()); retVal.setDriver(new org.h2.Driver());
retVal.setUrl("jdbc:derby:memory:myUnitTestDBDstu2;create=true"); retVal.setUrl("jdbc:h2:mem:testdb_dstu2");
retVal.setMaxWaitMillis(10000); retVal.setMaxWaitMillis(10000);
retVal.setUsername(""); retVal.setUsername("");
retVal.setPassword(""); retVal.setPassword("");
@ -139,7 +140,7 @@ public class TestDstu2Config extends BaseJavaConfigDstu2 {
extraProperties.put("hibernate.format_sql", "true"); extraProperties.put("hibernate.format_sql", "true");
extraProperties.put("hibernate.show_sql", "false"); extraProperties.put("hibernate.show_sql", "false");
extraProperties.put("hibernate.hbm2ddl.auto", "update"); 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.model_mapping", LuceneSearchMappingFactory.class.getName());
extraProperties.put("hibernate.search.default.directory_provider", "local-heap"); extraProperties.put("hibernate.search.default.directory_provider", "local-heap");
extraProperties.put("hibernate.search.lucene_version", "LUCENE_CURRENT"); extraProperties.put("hibernate.search.lucene_version", "LUCENE_CURRENT");

View File

@ -9,6 +9,7 @@ import ca.uhn.fhir.rest.server.interceptor.RequestValidatingInterceptor;
import ca.uhn.fhir.validation.ResultSeverityEnum; import ca.uhn.fhir.validation.ResultSeverityEnum;
import net.ttddyy.dsproxy.support.ProxyDataSourceBuilder; import net.ttddyy.dsproxy.support.ProxyDataSourceBuilder;
import org.apache.commons.dbcp2.BasicDataSource; import org.apache.commons.dbcp2.BasicDataSource;
import org.hibernate.dialect.H2Dialect;
import org.springframework.context.annotation.*; import org.springframework.context.annotation.*;
import org.springframework.context.support.PropertySourcesPlaceholderConfigurer; import org.springframework.context.support.PropertySourcesPlaceholderConfigurer;
import org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean; import org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean;
@ -81,8 +82,8 @@ public class TestDstu3Config extends BaseJavaConfigDstu3 {
} }
}; };
retVal.setDriver(new org.apache.derby.jdbc.EmbeddedDriver()); retVal.setDriver(new org.h2.Driver());
retVal.setUrl("jdbc:derby:memory:myUnitTestDBDstu3;create=true"); retVal.setUrl("jdbc:h2:mem:testdb_dstu3");
retVal.setMaxWaitMillis(10000); retVal.setMaxWaitMillis(10000);
retVal.setUsername(""); retVal.setUsername("");
retVal.setPassword(""); retVal.setPassword("");
@ -138,7 +139,7 @@ public class TestDstu3Config extends BaseJavaConfigDstu3 {
extraProperties.put("hibernate.format_sql", "false"); extraProperties.put("hibernate.format_sql", "false");
extraProperties.put("hibernate.show_sql", "false"); extraProperties.put("hibernate.show_sql", "false");
extraProperties.put("hibernate.hbm2ddl.auto", "update"); 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.model_mapping", LuceneSearchMappingFactory.class.getName());
extraProperties.put("hibernate.search.default.directory_provider", "local-heap"); extraProperties.put("hibernate.search.default.directory_provider", "local-heap");
extraProperties.put("hibernate.search.lucene_version", "LUCENE_CURRENT"); extraProperties.put("hibernate.search.lucene_version", "LUCENE_CURRENT");

View File

@ -2,6 +2,7 @@ package ca.uhn.fhir.jpa.config;
import java.util.Properties; import java.util.Properties;
import org.hibernate.dialect.H2Dialect;
import org.hibernate.jpa.HibernatePersistenceProvider; import org.hibernate.jpa.HibernatePersistenceProvider;
import org.springframework.beans.factory.annotation.Autowire; import org.springframework.beans.factory.annotation.Autowire;
import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Bean;
@ -37,7 +38,7 @@ public class TestDstu3WithoutLuceneConfig extends TestDstu3Config {
extraProperties.put("hibernate.format_sql", "false"); extraProperties.put("hibernate.format_sql", "false");
extraProperties.put("hibernate.show_sql", "false"); extraProperties.put("hibernate.show_sql", "false");
extraProperties.put("hibernate.hbm2ddl.auto", "update"); 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"); extraProperties.put("hibernate.search.autoregister_listeners", "false");
return extraProperties; return extraProperties;
} }

View File

@ -7,6 +7,7 @@ import ca.uhn.fhir.validation.ResultSeverityEnum;
import net.ttddyy.dsproxy.listener.SingleQueryCountHolder; import net.ttddyy.dsproxy.listener.SingleQueryCountHolder;
import net.ttddyy.dsproxy.support.ProxyDataSourceBuilder; import net.ttddyy.dsproxy.support.ProxyDataSourceBuilder;
import org.apache.commons.dbcp2.BasicDataSource; import org.apache.commons.dbcp2.BasicDataSource;
import org.hibernate.dialect.H2Dialect;
import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration; import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.Import; import org.springframework.context.annotation.Import;
@ -16,7 +17,6 @@ import org.springframework.transaction.annotation.EnableTransactionManagement;
import javax.sql.DataSource; import javax.sql.DataSource;
import java.sql.Connection; import java.sql.Connection;
import java.sql.SQLException;
import java.util.Properties; import java.util.Properties;
import static org.junit.Assert.fail; import static org.junit.Assert.fail;
@ -53,17 +53,14 @@ public class TestR4Config extends BaseJavaConfigR4 {
@Override @Override
public Connection getConnection() throws SQLException { public Connection getConnection() {
ConnectionWrapper retVal; ConnectionWrapper retVal;
try { try {
retVal = new ConnectionWrapper(super.getConnection()); retVal = new ConnectionWrapper(super.getConnection());
} catch (Exception e) { } catch (Exception e) {
ourLog.error("Exceeded maximum wait for connection", e); ourLog.error("Exceeded maximum wait for connection", e);
logGetConnectionStackTrace(); logGetConnectionStackTrace();
// if ("true".equals(System.getStringProperty("ci"))) {
fail("Exceeded maximum wait for connection: " + e.toString()); fail("Exceeded maximum wait for connection: " + e.toString());
// }
// System.exit(1);
retVal = null; retVal = null;
} }
@ -94,8 +91,8 @@ public class TestR4Config extends BaseJavaConfigR4 {
} }
}; };
retVal.setDriver(new org.apache.derby.jdbc.EmbeddedDriver()); retVal.setDriver(new org.h2.Driver());
retVal.setUrl("jdbc:derby:memory:myUnitTestDBR4;create=true"); retVal.setUrl("jdbc:h2:mem:testdb_r4");
retVal.setMaxWaitMillis(10000); retVal.setMaxWaitMillis(10000);
retVal.setUsername(""); retVal.setUsername("");
retVal.setPassword(""); retVal.setPassword("");
@ -135,7 +132,7 @@ public class TestR4Config extends BaseJavaConfigR4 {
extraProperties.put("hibernate.format_sql", "false"); extraProperties.put("hibernate.format_sql", "false");
extraProperties.put("hibernate.show_sql", "false"); extraProperties.put("hibernate.show_sql", "false");
extraProperties.put("hibernate.hbm2ddl.auto", "update"); 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.model_mapping", ca.uhn.fhir.jpa.search.LuceneSearchMappingFactory.class.getName());
extraProperties.put("hibernate.search.default.directory_provider", "local-heap"); extraProperties.put("hibernate.search.default.directory_provider", "local-heap");
extraProperties.put("hibernate.search.lucene_version", "LUCENE_CURRENT"); extraProperties.put("hibernate.search.lucene_version", "LUCENE_CURRENT");

View File

@ -2,6 +2,7 @@ package ca.uhn.fhir.jpa.config;
import java.util.Properties; import java.util.Properties;
import org.hibernate.dialect.H2Dialect;
import org.hibernate.jpa.HibernatePersistenceProvider; import org.hibernate.jpa.HibernatePersistenceProvider;
import org.springframework.beans.factory.annotation.Autowire; import org.springframework.beans.factory.annotation.Autowire;
import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Bean;
@ -38,7 +39,7 @@ public class TestR4WithoutLuceneConfig extends TestR4Config {
extraProperties.put("hibernate.format_sql", "false"); extraProperties.put("hibernate.format_sql", "false");
extraProperties.put("hibernate.show_sql", "false"); extraProperties.put("hibernate.show_sql", "false");
extraProperties.put("hibernate.hbm2ddl.auto", "update"); 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"); extraProperties.put("hibernate.search.autoregister_listeners", "false");
return extraProperties; return extraProperties;
} }

View File

@ -77,6 +77,7 @@ public abstract class BaseJpaTest {
static { static {
System.setProperty(Constants.TEST_SYSTEM_PROP_VALIDATION_RESOURCE_CACHES_MS, "1000"); System.setProperty(Constants.TEST_SYSTEM_PROP_VALIDATION_RESOURCE_CACHES_MS, "1000");
System.setProperty("test", "true"); System.setProperty("test", "true");
TestUtil.setShouldRandomizeTimezones(false);
} }
@Rule @Rule

View File

@ -750,10 +750,9 @@ public class FhirResourceDaoDstu2SearchNoFtTest extends BaseJpaDstu2Test {
public void testSearchLastUpdatedParam() throws InterruptedException { public void testSearchLastUpdatedParam() throws InterruptedException {
String methodName = "testSearchLastUpdatedParam"; String methodName = "testSearchLastUpdatedParam";
int sleep = 100;
Thread.sleep(sleep);
DateTimeDt beforeAny = new DateTimeDt(new Date(), TemporalPrecisionEnum.MILLI); DateTimeDt beforeAny = new DateTimeDt(new Date(), TemporalPrecisionEnum.MILLI);
TestUtil.sleepOneClick();
IIdType id1a; IIdType id1a;
{ {
Patient patient = new Patient(); Patient patient = new Patient();
@ -769,9 +768,9 @@ public class FhirResourceDaoDstu2SearchNoFtTest extends BaseJpaDstu2Test {
id1b = myPatientDao.create(patient, mySrd).getId().toUnqualifiedVersionless(); id1b = myPatientDao.create(patient, mySrd).getId().toUnqualifiedVersionless();
} }
Thread.sleep(1100); TestUtil.sleepOneClick();
DateTimeDt beforeR2 = new DateTimeDt(new Date(), TemporalPrecisionEnum.MILLI); DateTimeDt beforeR2 = new DateTimeDt(new Date(), TemporalPrecisionEnum.MILLI);
Thread.sleep(1100); TestUtil.sleepOneClick();
IIdType id2; IIdType id2;
{ {

View File

@ -1,34 +1,18 @@
package ca.uhn.fhir.jpa.dao.dstu2; package ca.uhn.fhir.jpa.dao.dstu2;
import static org.apache.commons.lang3.StringUtils.defaultString; import ca.uhn.fhir.jpa.dao.BaseHapiFhirDao;
import static org.hamcrest.Matchers.*; import ca.uhn.fhir.jpa.dao.BaseHapiFhirResourceDao;
import static org.junit.Assert.*; import ca.uhn.fhir.jpa.dao.DaoConfig;
import static org.mockito.ArgumentMatchers.eq; import ca.uhn.fhir.jpa.dao.FhirResourceDaoDstu2;
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.dstu3.FhirResourceDaoDstu3Test; import ca.uhn.fhir.jpa.dao.dstu3.FhirResourceDaoDstu3Test;
import ca.uhn.fhir.jpa.model.entity.ResourceIndexedSearchParamString; import ca.uhn.fhir.jpa.model.entity.ResourceIndexedSearchParamString;
import ca.uhn.fhir.jpa.model.entity.TagTypeEnum; 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.api.*;
import ca.uhn.fhir.model.base.composite.BaseCodingDt; import ca.uhn.fhir.model.base.composite.BaseCodingDt;
import ca.uhn.fhir.model.dstu2.composite.*; import ca.uhn.fhir.model.dstu2.composite.*;
import ca.uhn.fhir.model.dstu2.resource.*; 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.dstu2.valueset.*;
import ca.uhn.fhir.model.primitive.*; import ca.uhn.fhir.model.primitive.*;
import ca.uhn.fhir.model.valueset.BundleEntrySearchModeEnum; 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.param.*;
import ca.uhn.fhir.rest.server.exceptions.*; import ca.uhn.fhir.rest.server.exceptions.*;
import ca.uhn.fhir.util.TestUtil; 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") @SuppressWarnings("unchecked")
public class FhirResourceDaoDstu2Test extends BaseJpaDstu2Test { public class FhirResourceDaoDstu2Test extends BaseJpaDstu2Test {
@ -750,7 +749,7 @@ public class FhirResourceDaoDstu2Test extends BaseJpaDstu2Test {
patient.addIdentifier().setSystem("ZZZZZZZ").setValue("ZZZZZZZZZ"); patient.addIdentifier().setSystem("ZZZZZZZ").setValue("ZZZZZZZZZ");
id2b = myPatientDao.update(patient, mySrd).getId(); 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(); SearchParameterMap params = new SearchParameterMap();
params.add(Patient.SP_FAMILY, new StringDt("Tester_testDeleteResource")); params.add(Patient.SP_FAMILY, new StringDt("Tester_testDeleteResource"));
@ -1555,28 +1554,28 @@ public class FhirResourceDaoDstu2Test extends BaseJpaDstu2Test {
public void testOrganizationName() { public void testOrganizationName() {
//@formatter:off //@formatter:off
String inputStr = String inputStr =
"{" + "{" +
" \"resourceType\":\"Organization\",\n" + " \"resourceType\":\"Organization\",\n" +
" \"extension\":[\n" + " \"extension\":[\n" +
" {\n" + " {\n" +
" \"url\":\"http://fhir.connectinggta.ca/Profile/organization#providerIdPool\",\n" + " \"url\":\"http://fhir.connectinggta.ca/Profile/organization#providerIdPool\",\n" +
" \"valueUri\":\"urn:oid:2.16.840.1.113883.3.239.23.21.1\"\n" + " \"valueUri\":\"urn:oid:2.16.840.1.113883.3.239.23.21.1\"\n" +
" }\n" + " }\n" +
" ],\n" + " ],\n" +
" \"text\":{\n" + " \"text\":{\n" +
" \"status\":\"empty\",\n" + " \"status\":\"empty\",\n" +
" \"div\":\"<div xmlns=\\\"http://www.w3.org/1999/xhtml\\\">No narrative template available for resource profile: http://fhir.connectinggta.ca/Profile/organization</div>\"\n" + " \"div\":\"<div xmlns=\\\"http://www.w3.org/1999/xhtml\\\">No narrative template available for resource profile: http://fhir.connectinggta.ca/Profile/organization</div>\"\n" +
" },\n" + " },\n" +
" \"identifier\":[\n" + " \"identifier\":[\n" +
" {\n" + " {\n" +
" \"use\":\"official\",\n" + " \"use\":\"official\",\n" +
" \"label\":\"HSP 2.16.840.1.113883.3.239.23.21\",\n" + " \"label\":\"HSP 2.16.840.1.113883.3.239.23.21\",\n" +
" \"system\":\"urn:cgta:hsp_ids\",\n" + " \"system\":\"urn:cgta:hsp_ids\",\n" +
" \"value\":\"urn:oid:2.16.840.1.113883.3.239.23.21\"\n" + " \"value\":\"urn:oid:2.16.840.1.113883.3.239.23.21\"\n" +
" }\n" + " }\n" +
" ],\n" + " ],\n" +
" \"name\":\"Peterborough Regional Health Centre\"\n" + " \"name\":\"Peterborough Regional Health Centre\"\n" +
"}\n"; "}\n";
//@formatter:on //@formatter:on
@ -1631,7 +1630,7 @@ public class FhirResourceDaoDstu2Test extends BaseJpaDstu2Test {
dr01.setSubject(new ResourceReferenceDt(patientId01)); dr01.setSubject(new ResourceReferenceDt(patientId01));
IIdType drId01 = myDiagnosticReportDao.create(dr01, mySrd).getId(); 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<Observation> result = toList(myObservationDao.search(new SearchParameterMap().setLoadSynchronous(true).add(Observation.SP_SUBJECT, new ReferenceParam(patientId01.getIdPart())))); List<Observation> result = toList(myObservationDao.search(new SearchParameterMap().setLoadSynchronous(true).add(Observation.SP_SUBJECT, new ReferenceParam(patientId01.getIdPart()))));
assertEquals(1, result.size()); assertEquals(1, result.size());
@ -2183,23 +2182,21 @@ public class FhirResourceDaoDstu2Test extends BaseJpaDstu2Test {
pm.setSort(new SortSpec(Patient.SP_BIRTHDATE)); pm.setSort(new SortSpec(Patient.SP_BIRTHDATE));
actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm));
assertEquals(4, actual.size()); assertEquals(4, actual.size());
assertThat(actual, contains(id1, id2, id3, id4)); assertThat(actual, contains(id4, id1, id2, id3));
pm = new SearchParameterMap(); pm = new SearchParameterMap();
pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", "testtestSortByDate")); pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", "testtestSortByDate"));
pm.setSort(new SortSpec(Patient.SP_BIRTHDATE).setOrder(SortOrderEnum.ASC)); pm.setSort(new SortSpec(Patient.SP_BIRTHDATE).setOrder(SortOrderEnum.ASC));
actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm));
assertEquals(4, actual.size()); assertEquals(4, actual.size());
assertThat(actual, contains(id1, id2, id3, id4)); assertThat(actual, contains(id4, id1, id2, id3));
pm = new SearchParameterMap(); pm = new SearchParameterMap();
pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", "testtestSortByDate")); pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", "testtestSortByDate"));
pm.setSort(new SortSpec(Patient.SP_BIRTHDATE).setOrder(SortOrderEnum.DESC)); pm.setSort(new SortSpec(Patient.SP_BIRTHDATE).setOrder(SortOrderEnum.DESC));
actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm));
assertEquals(4, actual.size()); 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(id3, id2, id1, id4));
assertThat(actual, contains(id4, id3, id2, id1));
} }
@ -2237,21 +2234,21 @@ public class FhirResourceDaoDstu2Test extends BaseJpaDstu2Test {
pm.setSort(new SortSpec(BaseResource.SP_RES_ID)); pm.setSort(new SortSpec(BaseResource.SP_RES_ID));
actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm));
assertEquals(5, actual.size()); assertEquals(5, actual.size());
assertThat(actual, contains(idMethodName, id1, id2, id3, id4)); assertThat(actual, contains(id1, id2, id3, id4, idMethodName));
pm = new SearchParameterMap(); pm = new SearchParameterMap();
pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", methodName)); pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", methodName));
pm.setSort(new SortSpec(BaseResource.SP_RES_ID).setOrder(SortOrderEnum.ASC)); pm.setSort(new SortSpec(BaseResource.SP_RES_ID).setOrder(SortOrderEnum.ASC));
actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm));
assertEquals(5, actual.size()); assertEquals(5, actual.size());
assertThat(actual, contains(idMethodName, id1, id2, id3, id4)); assertThat(actual, contains(id1, id2, id3, id4, idMethodName));
pm = new SearchParameterMap(); pm = new SearchParameterMap();
pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", methodName)); pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", methodName));
pm.setSort(new SortSpec(BaseResource.SP_RES_ID).setOrder(SortOrderEnum.DESC)); pm.setSort(new SortSpec(BaseResource.SP_RES_ID).setOrder(SortOrderEnum.DESC));
actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm));
assertEquals(5, actual.size()); assertEquals(5, actual.size());
assertThat(actual, contains(id4, id3, id2, id1, idMethodName)); assertThat(actual, contains(idMethodName, id4, id3, id2, id1));
} }
@Test @Test
@ -2477,23 +2474,21 @@ public class FhirResourceDaoDstu2Test extends BaseJpaDstu2Test {
pm.setSort(new SortSpec(Patient.SP_FAMILY)); pm.setSort(new SortSpec(Patient.SP_FAMILY));
actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm));
assertEquals(4, actual.size()); assertEquals(4, actual.size());
assertThat(actual, contains(id1, id2, id3, id4)); assertThat(actual, contains(id4, id1, id2, id3));
pm = new SearchParameterMap(); pm = new SearchParameterMap();
pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", string)); pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", string));
pm.setSort(new SortSpec(Patient.SP_FAMILY).setOrder(SortOrderEnum.ASC)); pm.setSort(new SortSpec(Patient.SP_FAMILY).setOrder(SortOrderEnum.ASC));
actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm));
assertEquals(4, actual.size()); assertEquals(4, actual.size());
assertThat(actual, contains(id1, id2, id3, id4)); assertThat(actual, contains(id4, id1, id2, id3));
pm = new SearchParameterMap(); pm = new SearchParameterMap();
pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", string)); pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", string));
pm.setSort(new SortSpec(Patient.SP_FAMILY).setOrder(SortOrderEnum.DESC)); pm.setSort(new SortSpec(Patient.SP_FAMILY).setOrder(SortOrderEnum.DESC));
actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm));
assertEquals(4, actual.size()); 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(id3, id2, id1, id4));
assertThat(actual, contains(id4, id3, id2, id1));
} }
/** /**

View File

@ -1138,10 +1138,9 @@ public class FhirResourceDaoDstu3SearchNoFtTest extends BaseJpaDstu3Test {
public void testSearchLastUpdatedParam() throws InterruptedException { public void testSearchLastUpdatedParam() throws InterruptedException {
String methodName = "testSearchLastUpdatedParam"; String methodName = "testSearchLastUpdatedParam";
int sleep = 100;
Thread.sleep(sleep);
DateTimeType beforeAny = new DateTimeType(new Date(), TemporalPrecisionEnum.MILLI); DateTimeType beforeAny = new DateTimeType(new Date(), TemporalPrecisionEnum.MILLI);
TestUtil.sleepOneClick();
IIdType id1a; IIdType id1a;
{ {
Patient patient = new Patient(); Patient patient = new Patient();
@ -1157,9 +1156,9 @@ public class FhirResourceDaoDstu3SearchNoFtTest extends BaseJpaDstu3Test {
id1b = myPatientDao.create(patient, mySrd).getId().toUnqualifiedVersionless(); id1b = myPatientDao.create(patient, mySrd).getId().toUnqualifiedVersionless();
} }
Thread.sleep(1100); TestUtil.sleepOneClick();
DateTimeType beforeR2 = new DateTimeType(new Date(), TemporalPrecisionEnum.MILLI); DateTimeType beforeR2 = new DateTimeType(new Date(), TemporalPrecisionEnum.MILLI);
Thread.sleep(1100); TestUtil.sleepOneClick();
IIdType id2; IIdType id2;
{ {
@ -1220,9 +1219,8 @@ public class FhirResourceDaoDstu3SearchNoFtTest extends BaseJpaDstu3Test {
} }
@SuppressWarnings("deprecation")
@Test @Test
public void testSearchLastUpdatedParamWithComparator() throws InterruptedException { public void testSearchLastUpdatedParamWithComparator() {
IIdType id0; IIdType id0;
{ {
Patient patient = new Patient(); Patient patient = new Patient();
@ -3215,12 +3213,12 @@ public class FhirResourceDaoDstu3SearchNoFtTest extends BaseJpaDstu3Test {
map = new SearchParameterMap(); map = new SearchParameterMap();
map.setSort(new SortSpec("_id", SortOrderEnum.ASC)); map.setSort(new SortSpec("_id", SortOrderEnum.ASC));
ids = toUnqualifiedVersionlessIdValues(myPatientDao.search(map)); ids = toUnqualifiedVersionlessIdValues(myPatientDao.search(map));
assertThat(ids, contains("Patient/AA", "Patient/AB", id1, id2)); assertThat(ids, contains(id1, id2, "Patient/AA", "Patient/AB"));
} }
@Test @Test
public void testSortOnLastUpdated() throws Exception { public void testSortOnLastUpdated() {
// Numeric ID // Numeric ID
Patient p01 = new Patient(); Patient p01 = new Patient();
p01.setActive(true); p01.setActive(true);
@ -3371,13 +3369,13 @@ public class FhirResourceDaoDstu3SearchNoFtTest extends BaseJpaDstu3Test {
map = new SearchParameterMap(); map = new SearchParameterMap();
map.setSort(new SortSpec(Patient.SP_FAMILY, SortOrderEnum.ASC).setChain(new SortSpec(Patient.SP_GIVEN, SortOrderEnum.ASC))); map.setSort(new SortSpec(Patient.SP_FAMILY, SortOrderEnum.ASC).setChain(new SortSpec(Patient.SP_GIVEN, SortOrderEnum.ASC)));
ids = toUnqualifiedVersionlessIds(myPatientDao.search(map)); 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()); assertEquals(5, ids.size());
} }
@Test @Test
public void testSortOnSparselyPopulatedSearchParameter() throws Exception { public void testSortOnSparselyPopulatedSearchParameter() {
Patient pCA = new Patient(); Patient pCA = new Patient();
pCA.setId("CA"); pCA.setId("CA");
pCA.setActive(false); pCA.setActive(false);
@ -3421,19 +3419,19 @@ public class FhirResourceDaoDstu3SearchNoFtTest extends BaseJpaDstu3Test {
map.setSort(new SortSpec("gender")); map.setSort(new SortSpec("gender"));
ids = toUnqualifiedVersionlessIdValues(myPatientDao.search(map)); ids = toUnqualifiedVersionlessIdValues(myPatientDao.search(map));
ourLog.info("IDS: {}", ids); 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 = new SearchParameterMap();
map.setSort(new SortSpec("gender").setChain(new SortSpec("family", SortOrderEnum.ASC).setChain(new SortSpec("given", SortOrderEnum.ASC)))); map.setSort(new SortSpec("gender").setChain(new SortSpec("family", SortOrderEnum.ASC).setChain(new SortSpec("given", SortOrderEnum.ASC))));
ids = toUnqualifiedVersionlessIdValues(myPatientDao.search(map)); ids = toUnqualifiedVersionlessIdValues(myPatientDao.search(map));
ourLog.info("IDS: {}", ids); 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 = new SearchParameterMap();
map.add(Patient.SP_ACTIVE, new TokenParam(null, "true")); map.add(Patient.SP_ACTIVE, new TokenParam(null, "true"));
map.setSort(new SortSpec("family", SortOrderEnum.ASC).setChain(new SortSpec("given", SortOrderEnum.ASC))); map.setSort(new SortSpec("family", SortOrderEnum.ASC).setChain(new SortSpec("given", SortOrderEnum.ASC)));
ids = toUnqualifiedVersionlessIdValues(myPatientDao.search(map)); 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) { private String toStringMultiline(List<?> theResults) {

View File

@ -1,6 +1,9 @@
package ca.uhn.fhir.jpa.dao.dstu3; 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.ResourceIndexedSearchParamString;
import ca.uhn.fhir.jpa.model.entity.TagTypeEnum; import ca.uhn.fhir.jpa.model.entity.TagTypeEnum;
import ca.uhn.fhir.jpa.searchparam.SearchParamConstants; 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.BundleEntrySearchModeEnum;
import ca.uhn.fhir.model.valueset.BundleEntryTransactionMethodEnum; import ca.uhn.fhir.model.valueset.BundleEntryTransactionMethodEnum;
import ca.uhn.fhir.rest.api.Constants; 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.api.server.IBundleProvider;
import ca.uhn.fhir.rest.param.*; import ca.uhn.fhir.rest.param.*;
import ca.uhn.fhir.rest.server.exceptions.*; import ca.uhn.fhir.rest.server.exceptions.*;
@ -41,10 +46,8 @@ import org.springframework.transaction.support.TransactionTemplate;
import java.util.*; import java.util.*;
import static org.apache.commons.lang3.StringUtils.defaultString; import static org.apache.commons.lang3.StringUtils.defaultString;
import static org.hamcrest.Matchers.contains;
import static org.hamcrest.Matchers.*; import static org.hamcrest.Matchers.*;
import static org.junit.Assert.*; import static org.junit.Assert.*;
import static org.mockito.ArgumentMatchers.eq;
@SuppressWarnings({"unchecked", "deprecation"}) @SuppressWarnings({"unchecked", "deprecation"})
public class FhirResourceDaoDstu3Test extends BaseJpaDstu3Test { public class FhirResourceDaoDstu3Test extends BaseJpaDstu3Test {
@ -1035,7 +1038,7 @@ public class FhirResourceDaoDstu3Test extends BaseJpaDstu3Test {
patient.addIdentifier().setSystem("ZZZZZZZ").setValue("ZZZZZZZZZ"); patient.addIdentifier().setSystem("ZZZZZZZ").setValue("ZZZZZZZZZ");
id2b = myPatientDao.update(patient, mySrd).getId(); 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(); SearchParameterMap params = new SearchParameterMap();
params.setLoadSynchronous(true); params.setLoadSynchronous(true);
@ -2078,7 +2081,7 @@ public class FhirResourceDaoDstu3Test extends BaseJpaDstu3Test {
dr01.setSubject(new Reference(patientId01)); dr01.setSubject(new Reference(patientId01));
IIdType drId01 = myDiagnosticReportDao.create(dr01, mySrd).getId(); 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<Observation> result = toList(myObservationDao.search(new SearchParameterMap(Observation.SP_SUBJECT, new ReferenceParam(patientId01.getIdPart())).setLoadSynchronous(true))); List<Observation> result = toList(myObservationDao.search(new SearchParameterMap(Observation.SP_SUBJECT, new ReferenceParam(patientId01.getIdPart())).setLoadSynchronous(true)));
assertEquals(1, result.size()); assertEquals(1, result.size());
@ -2695,23 +2698,21 @@ public class FhirResourceDaoDstu3Test extends BaseJpaDstu3Test {
pm.setSort(new SortSpec(Patient.SP_BIRTHDATE)); pm.setSort(new SortSpec(Patient.SP_BIRTHDATE));
actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm));
assertEquals(4, actual.size()); assertEquals(4, actual.size());
assertThat(actual, contains(id1, id2, id3, id4)); assertThat(actual, contains(id4, id1, id2, id3));
pm = new SearchParameterMap(); pm = new SearchParameterMap();
pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", "testtestSortByDate")); pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", "testtestSortByDate"));
pm.setSort(new SortSpec(Patient.SP_BIRTHDATE).setOrder(SortOrderEnum.ASC)); pm.setSort(new SortSpec(Patient.SP_BIRTHDATE).setOrder(SortOrderEnum.ASC));
actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm));
assertEquals(4, actual.size()); assertEquals(4, actual.size());
assertThat(actual, contains(id1, id2, id3, id4)); assertThat(actual, contains(id4, id1, id2, id3));
pm = new SearchParameterMap(); pm = new SearchParameterMap();
pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", "testtestSortByDate")); pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", "testtestSortByDate"));
pm.setSort(new SortSpec(Patient.SP_BIRTHDATE).setOrder(SortOrderEnum.DESC)); pm.setSort(new SortSpec(Patient.SP_BIRTHDATE).setOrder(SortOrderEnum.DESC));
actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm));
assertEquals(4, actual.size()); 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(id3, id2, id1, id4));
assertThat(actual, contains(id4, id3, id2, id1));
} }
@ -2749,21 +2750,21 @@ public class FhirResourceDaoDstu3Test extends BaseJpaDstu3Test {
pm.setSort(new SortSpec(IAnyResource.SP_RES_ID)); pm.setSort(new SortSpec(IAnyResource.SP_RES_ID));
actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm));
assertEquals(5, actual.size()); 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 = new SearchParameterMap();
pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", methodName)); pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", methodName));
pm.setSort(new SortSpec(IAnyResource.SP_RES_ID).setOrder(SortOrderEnum.ASC)); pm.setSort(new SortSpec(IAnyResource.SP_RES_ID).setOrder(SortOrderEnum.ASC));
actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm));
assertEquals(5, actual.size()); 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 = new SearchParameterMap();
pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", methodName)); pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", methodName));
pm.setSort(new SortSpec(IAnyResource.SP_RES_ID).setOrder(SortOrderEnum.DESC)); pm.setSort(new SortSpec(IAnyResource.SP_RES_ID).setOrder(SortOrderEnum.DESC));
actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm));
assertEquals(5, actual.size()); assertEquals(5, actual.size());
assertThat(actual, contains(id4, id3, id2, id1, idMethodName)); assertThat(actual.toString(), actual, contains(idMethodName, id4, id3, id2, id1));
} }
@Test @Test
@ -2988,23 +2989,21 @@ public class FhirResourceDaoDstu3Test extends BaseJpaDstu3Test {
pm.setSort(new SortSpec(Patient.SP_FAMILY)); pm.setSort(new SortSpec(Patient.SP_FAMILY));
actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm));
assertEquals(4, actual.size()); assertEquals(4, actual.size());
assertThat(actual, contains(id1, id2, id3, id4)); assertThat(actual, contains(id4, id1, id2, id3));
pm = new SearchParameterMap(); pm = new SearchParameterMap();
pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", string)); pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", string));
pm.setSort(new SortSpec(Patient.SP_FAMILY).setOrder(SortOrderEnum.ASC)); pm.setSort(new SortSpec(Patient.SP_FAMILY).setOrder(SortOrderEnum.ASC));
actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm));
assertEquals(4, actual.size()); assertEquals(4, actual.size());
assertThat(actual, contains(id1, id2, id3, id4)); assertThat(actual, contains(id4, id1, id2, id3));
pm = new SearchParameterMap(); pm = new SearchParameterMap();
pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", string)); pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", string));
pm.setSort(new SortSpec(Patient.SP_FAMILY).setOrder(SortOrderEnum.DESC)); pm.setSort(new SortSpec(Patient.SP_FAMILY).setOrder(SortOrderEnum.DESC));
actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm));
assertEquals(4, actual.size()); 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(id3, id2, id1, id4));
assertThat(actual, contains(id4, id3, id2, id1));
} }
/** /**

View File

@ -146,7 +146,10 @@ public class FhirResourceDaoR4SearchCustomSearchParamTest extends BaseJpaR4Test
mySearchParameterDao.create(fooSp, mySrd); mySearchParameterDao.create(fooSp, mySrd);
assertEquals(1, myResourceReindexingSvc.forceReindexingPass()); assertEquals(1, myResourceReindexingSvc.forceReindexingPass());
assertEquals(1, myResourceReindexingSvc.forceReindexingPass()); myResourceReindexingSvc.forceReindexingPass();
myResourceReindexingSvc.forceReindexingPass();
myResourceReindexingSvc.forceReindexingPass();
myResourceReindexingSvc.forceReindexingPass();
assertEquals(0, myResourceReindexingSvc.forceReindexingPass()); assertEquals(0, myResourceReindexingSvc.forceReindexingPass());
} }

View File

@ -1597,10 +1597,9 @@ public class FhirResourceDaoR4SearchNoFtTest extends BaseJpaR4Test {
public void testSearchLastUpdatedParam() throws InterruptedException { public void testSearchLastUpdatedParam() throws InterruptedException {
String methodName = "testSearchLastUpdatedParam"; String methodName = "testSearchLastUpdatedParam";
int sleep = 100;
Thread.sleep(sleep);
DateTimeType beforeAny = new DateTimeType(new Date(), TemporalPrecisionEnum.MILLI); DateTimeType beforeAny = new DateTimeType(new Date(), TemporalPrecisionEnum.MILLI);
TestUtil.sleepOneClick();
IIdType id1a; IIdType id1a;
{ {
Patient patient = new Patient(); Patient patient = new Patient();
@ -1616,9 +1615,9 @@ public class FhirResourceDaoR4SearchNoFtTest extends BaseJpaR4Test {
id1b = myPatientDao.create(patient, mySrd).getId().toUnqualifiedVersionless(); id1b = myPatientDao.create(patient, mySrd).getId().toUnqualifiedVersionless();
} }
Thread.sleep(1100); TestUtil.sleepOneClick();
DateTimeType beforeR2 = new DateTimeType(new Date(), TemporalPrecisionEnum.MILLI); DateTimeType beforeR2 = new DateTimeType(new Date(), TemporalPrecisionEnum.MILLI);
Thread.sleep(1100); TestUtil.sleepOneClick();
IIdType id2; IIdType id2;
{ {

View File

@ -51,6 +51,8 @@ public class FhirResourceDaoR4SearchOptimizedTest extends BaseJpaR4Test {
@Before @Before
public void before() { public void before() {
mySearchCoordinatorSvcImpl = (SearchCoordinatorSvcImpl) AopProxyUtils.getSingletonTarget(mySearchCoordinatorSvc); mySearchCoordinatorSvcImpl = (SearchCoordinatorSvcImpl) AopProxyUtils.getSingletonTarget(mySearchCoordinatorSvc);
mySearchCoordinatorSvcImpl.setLoadingThrottleForUnitTests(null);
mySearchCoordinatorSvcImpl.setSyncSizeForUnitTests(SearchCoordinatorSvcImpl.DEFAULT_SYNC_SIZE);
myCaptureQueriesListener.setCaptureQueryStackTrace(true); myCaptureQueriesListener.setCaptureQueryStackTrace(true);
} }
@ -121,7 +123,7 @@ public class FhirResourceDaoR4SearchOptimizedTest extends BaseJpaR4Test {
assertThat(ids, empty()); assertThat(ids, empty());
assertEquals(201, myDatabaseBackedPagingProvider.retrieveResultList(null, uuid).size().intValue()); assertEquals(201, myDatabaseBackedPagingProvider.retrieveResultList(null, uuid).size().intValue());
// Seach with total expicitly requested // Seach with total explicitly requested
params = new SearchParameterMap(); params = new SearchParameterMap();
params.add(Patient.SP_NAME, new StringParam("FAM")); params.add(Patient.SP_NAME, new StringParam("FAM"));
params.setSearchTotalMode(SearchTotalModeEnum.ACCURATE); params.setSearchTotalMode(SearchTotalModeEnum.ACCURATE);
@ -133,7 +135,7 @@ public class FhirResourceDaoR4SearchOptimizedTest extends BaseJpaR4Test {
assertThat(ids, hasSize(10)); assertThat(ids, hasSize(10));
assertEquals(201, myDatabaseBackedPagingProvider.retrieveResultList(null, uuid).size().intValue()); assertEquals(201, myDatabaseBackedPagingProvider.retrieveResultList(null, uuid).size().intValue());
// Seach with count only // Search with count only
params = new SearchParameterMap(); params = new SearchParameterMap();
params.add(Patient.SP_NAME, new StringParam().setMissing(false)); params.add(Patient.SP_NAME, new StringParam().setMissing(false));
params.setSummaryMode(SummaryEnum.COUNT); params.setSummaryMode(SummaryEnum.COUNT);
@ -148,7 +150,7 @@ public class FhirResourceDaoR4SearchOptimizedTest extends BaseJpaR4Test {
} }
@Test @Test
public void testFetchTotalAccurateForSlowLoading() { public void testFetchTotalAccurateForSlowLoading() throws InterruptedException {
create200Patients(); create200Patients();
mySearchCoordinatorSvcImpl.setLoadingThrottleForUnitTests(25); mySearchCoordinatorSvcImpl.setLoadingThrottleForUnitTests(25);
@ -171,6 +173,9 @@ public class FhirResourceDaoR4SearchOptimizedTest extends BaseJpaR4Test {
assertEquals("Patient/PT00000", ids.get(0)); assertEquals("Patient/PT00000", ids.get(0));
assertEquals("Patient/PT00004", ids.get(4)); 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); ourLog.info("** About to make new query for search with UUID: {}", uuid);
IBundleProvider search2 = myDatabaseBackedPagingProvider.retrieveResultList(null, uuid); IBundleProvider search2 = myDatabaseBackedPagingProvider.retrieveResultList(null, uuid);
Integer search2Size = search2.size(); Integer search2Size = search2.size();

View File

@ -83,8 +83,12 @@ public class FhirResourceDaoR4SortTest extends BaseJpaR4Test {
map = new SearchParameterMap(); map = new SearchParameterMap();
map.setSort(new SortSpec("_id", SortOrderEnum.ASC)); map.setSort(new SortSpec("_id", SortOrderEnum.ASC));
ids = toUnqualifiedVersionlessIdValues(myPatientDao.search(map)); 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 @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))); map.setSort(new SortSpec(Patient.SP_FAMILY, SortOrderEnum.ASC).setChain(new SortSpec(Patient.SP_GIVEN, SortOrderEnum.ASC)));
ids = toUnqualifiedVersionlessIds(myPatientDao.search(map)); ids = toUnqualifiedVersionlessIds(myPatientDao.search(map));
ourLog.info("** Got IDs: {}", ids); 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()); 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)))); map.setSort(new SortSpec("gender").setChain(new SortSpec("family", SortOrderEnum.ASC).setChain(new SortSpec("given", SortOrderEnum.ASC))));
ids = toUnqualifiedVersionlessIdValues(myPatientDao.search(map)); ids = toUnqualifiedVersionlessIdValues(myPatientDao.search(map));
ourLog.info("IDS: {}", ids); 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 = new SearchParameterMap();
map.add(Patient.SP_ACTIVE, new TokenParam(null, "true")); map.add(Patient.SP_ACTIVE, new TokenParam(null, "true"));

View File

@ -27,6 +27,7 @@ import org.junit.*;
import org.springframework.beans.factory.annotation.Autowired; import org.springframework.beans.factory.annotation.Autowired;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.Date;
import java.util.List; import java.util.List;
import java.util.Set; import java.util.Set;
import java.util.stream.Collectors; import java.util.stream.Collectors;
@ -253,12 +254,17 @@ public class FhirResourceDaoR4TerminologyTest extends BaseJpaR4Test {
public void testConceptTimestamps() { public void testConceptTimestamps() {
long start = System.currentTimeMillis() - 10; long start = System.currentTimeMillis() - 10;
runInTransaction(() -> {
List<TermConcept> concepts = myTermConceptDao.findAll();
assertThat(concepts, empty());
});
createExternalCsDogs(); createExternalCsDogs();
runInTransaction(() -> { runInTransaction(() -> {
List<TermConcept> concepts = myTermConceptDao.findAll(); List<TermConcept> concepts = myTermConceptDao.findAll();
for (TermConcept next : concepts) { 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);
} }
}); });
} }

View File

@ -3031,23 +3031,24 @@ public class FhirResourceDaoR4Test extends BaseJpaR4Test {
pm.setSort(new SortSpec(Patient.SP_BIRTHDATE)); pm.setSort(new SortSpec(Patient.SP_BIRTHDATE));
actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm));
assertEquals(4, actual.size()); 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 = new SearchParameterMap();
pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", "testtestSortByDate")); pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", "testtestSortByDate"));
pm.setSort(new SortSpec(Patient.SP_BIRTHDATE).setOrder(SortOrderEnum.ASC)); pm.setSort(new SortSpec(Patient.SP_BIRTHDATE).setOrder(SortOrderEnum.ASC));
actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm));
assertEquals(4, actual.size()); 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 = new SearchParameterMap();
pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", "testtestSortByDate")); pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", "testtestSortByDate"));
pm.setSort(new SortSpec(Patient.SP_BIRTHDATE).setOrder(SortOrderEnum.DESC)); pm.setSort(new SortSpec(Patient.SP_BIRTHDATE).setOrder(SortOrderEnum.DESC));
actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm));
assertEquals(4, actual.size()); 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(id3, id2, id1, id4)); // assertThat(actual, contains(id4, id3, id2, id1));
assertThat(actual, contains(id4, id3, id2, id1));
} }
@ -3119,21 +3120,21 @@ public class FhirResourceDaoR4Test extends BaseJpaR4Test {
pm.setSort(new SortSpec(IAnyResource.SP_RES_ID)); pm.setSort(new SortSpec(IAnyResource.SP_RES_ID));
actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm));
assertEquals(5, actual.size()); assertEquals(5, actual.size());
assertThat(actual, contains(idMethodName, id1, id2, id3, id4)); assertThat(actual, contains(id1, id2, id3, id4, idMethodName));
pm = new SearchParameterMap(); pm = new SearchParameterMap();
pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", methodName)); pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", methodName));
pm.setSort(new SortSpec(IAnyResource.SP_RES_ID).setOrder(SortOrderEnum.ASC)); pm.setSort(new SortSpec(IAnyResource.SP_RES_ID).setOrder(SortOrderEnum.ASC));
actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm));
assertEquals(5, actual.size()); assertEquals(5, actual.size());
assertThat(actual, contains(idMethodName, id1, id2, id3, id4)); assertThat(actual, contains(id1, id2, id3, id4, idMethodName));
pm = new SearchParameterMap(); pm = new SearchParameterMap();
pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", methodName)); pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", methodName));
pm.setSort(new SortSpec(IAnyResource.SP_RES_ID).setOrder(SortOrderEnum.DESC)); pm.setSort(new SortSpec(IAnyResource.SP_RES_ID).setOrder(SortOrderEnum.DESC));
actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm));
assertEquals(5, actual.size()); assertEquals(5, actual.size());
assertThat(actual, contains(id4, id3, id2, id1, idMethodName)); assertThat(actual, contains(idMethodName, id4, id3, id2, id1));
} }
@Test @Test
@ -3357,23 +3358,22 @@ public class FhirResourceDaoR4Test extends BaseJpaR4Test {
pm.setSort(new SortSpec(Patient.SP_FAMILY)); pm.setSort(new SortSpec(Patient.SP_FAMILY));
actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm));
assertEquals(4, actual.size()); assertEquals(4, actual.size());
assertThat(actual, contains(id1, id2, id3, id4)); assertThat(actual, contains(id4, id1, id2, id3));
pm = new SearchParameterMap(); pm = new SearchParameterMap();
pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", string)); pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", string));
pm.setSort(new SortSpec(Patient.SP_FAMILY).setOrder(SortOrderEnum.ASC)); pm.setSort(new SortSpec(Patient.SP_FAMILY).setOrder(SortOrderEnum.ASC));
actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm));
assertEquals(4, actual.size()); assertEquals(4, actual.size());
assertThat(actual, contains(id1, id2, id3, id4)); assertThat(actual, contains(id4, id1, id2, id3));
pm = new SearchParameterMap(); pm = new SearchParameterMap();
pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", string)); pm.add(Patient.SP_IDENTIFIER, new TokenParam("urn:system", string));
pm.setSort(new SortSpec(Patient.SP_FAMILY).setOrder(SortOrderEnum.DESC)); pm.setSort(new SortSpec(Patient.SP_FAMILY).setOrder(SortOrderEnum.DESC));
actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm)); actual = toUnqualifiedVersionlessIds(myPatientDao.search(pm));
assertEquals(4, actual.size()); 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(id3, id2, id1, id4)); // assertThat(actual, contains(id4, id3, id2, id1));
assertThat(actual, contains(id4, id3, id2, id1));
} }
/** /**

View File

@ -72,6 +72,8 @@ import java.nio.charset.StandardCharsets;
import java.util.*; import java.util.*;
import java.util.stream.Collectors; 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.apache.commons.lang3.StringUtils.isNotBlank;
import static org.hamcrest.Matchers.*; import static org.hamcrest.Matchers.*;
import static org.junit.Assert.*; import static org.junit.Assert.*;
@ -525,9 +527,11 @@ public class ResourceProviderR4Test extends BaseResourceProviderR4Test {
assertEquals(1, exts.size()); assertEquals(1, exts.size());
} }
private List<String> searchAndReturnUnqualifiedIdValues(String uri) throws IOException { private List<String> searchAndReturnUnqualifiedIdValues(String theUri) throws IOException {
List<String> ids; List<String> ids;
HttpGet get = new HttpGet(uri); HttpGet get = new HttpGet(theUri);
ourLog.info("About to perform search for: {}", theUri);
CloseableHttpResponse response = ourHttpClient.execute(get); CloseableHttpResponse response = ourHttpClient.execute(get);
try { try {
@ -2320,12 +2324,13 @@ public class ResourceProviderR4Test extends BaseResourceProviderR4Test {
List<Date> preDates = Lists.newArrayList(); List<Date> preDates = Lists.newArrayList();
List<String> ids = Lists.newArrayList(); List<String> ids = Lists.newArrayList();
for (int i = 0; i < 10; i++) { for (int i = 0; i < 10; i++) {
Thread.sleep(100); sleepOneClick();
preDates.add(new Date()); preDates.add(new Date());
Thread.sleep(100); sleepOneClick();
patient.setId(id); patient.setId(id);
patient.getName().get(0).getFamilyElement().setValue(methodName + "_i" + i); patient.getName().get(0).getFamilyElement().setValue(methodName + "_i" + i);
ids.add(myPatientDao.update(patient, mySrd).getId().toUnqualified().getValue()); ids.add(myPatientDao.update(patient, mySrd).getId().toUnqualified().getValue());
sleepOneClick();
} }
List<String> idValues; List<String> idValues;
@ -3976,7 +3981,7 @@ public class ResourceProviderR4Test extends BaseResourceProviderR4Test {
Search search1 = newTxTemplate().execute(theStatus -> mySearchEntityDao.findByUuid(uuid1)); Search search1 = newTxTemplate().execute(theStatus -> mySearchEntityDao.findByUuid(uuid1));
Date lastReturned1 = search1.getSearchLastReturned(); Date lastReturned1 = search1.getSearchLastReturned();
TestUtil.sleepOneClick(); sleepOneClick();
Bundle result2 = ourClient Bundle result2 = ourClient
.search() .search()

View File

@ -37,6 +37,7 @@ import org.slf4j.LoggerFactory;
import org.springframework.data.domain.PageImpl; import org.springframework.data.domain.PageImpl;
import org.springframework.data.domain.Pageable; import org.springframework.data.domain.Pageable;
import org.springframework.transaction.PlatformTransactionManager; import org.springframework.transaction.PlatformTransactionManager;
import org.springframework.transaction.TransactionStatus;
import javax.persistence.EntityManager; import javax.persistence.EntityManager;
import java.util.*; import java.util.*;
@ -100,6 +101,8 @@ public class SearchCoordinatorSvcImplTest {
when(myCallingDao.newSearchBuilder()).thenReturn(mySearchBuider); when(myCallingDao.newSearchBuilder()).thenReturn(mySearchBuider);
when(myTxManager.getTransaction(any())).thenReturn(mock(TransactionStatus.class));
doAnswer(theInvocation -> { doAnswer(theInvocation -> {
PersistedJpaBundleProvider provider = (PersistedJpaBundleProvider) theInvocation.getArguments()[0]; PersistedJpaBundleProvider provider = (PersistedJpaBundleProvider) theInvocation.getArguments()[0];
provider.setSearchCoordinatorSvc(mySvc); provider.setSearchCoordinatorSvc(mySvc);

View File

@ -82,14 +82,13 @@ public abstract class BaseHasResource implements IBaseResourceEntity {
@Override @Override
public Date getDeleted() { public Date getDeleted() {
return myDeleted; return cloneDate(myDeleted);
} }
public void setDeleted(Date theDate) { public void setDeleted(Date theDate) {
myDeleted = theDate; myDeleted = theDate;
} }
@Override @Override
public FhirVersionEnum getFhirVersion() { public FhirVersionEnum getFhirVersion() {
return myFhirVersion; return myFhirVersion;
@ -125,7 +124,7 @@ public abstract class BaseHasResource implements IBaseResourceEntity {
@Override @Override
public InstantDt getPublished() { public InstantDt getPublished() {
if (myPublished != null) { if (myPublished != null) {
return new InstantDt(myPublished); return new InstantDt(cloneDate(myPublished));
} else { } else {
return null; return null;
} }
@ -149,7 +148,7 @@ public abstract class BaseHasResource implements IBaseResourceEntity {
@Override @Override
public InstantDt getUpdated() { public InstantDt getUpdated() {
return new InstantDt(myUpdated); return new InstantDt(cloneDate(myUpdated));
} }
public void setUpdated(Date theUpdated) { public void setUpdated(Date theUpdated) {
@ -162,7 +161,7 @@ public abstract class BaseHasResource implements IBaseResourceEntity {
@Override @Override
public Date getUpdatedDate() { public Date getUpdatedDate() {
return myUpdated; return cloneDate(myUpdated);
} }
@Override @Override
@ -177,4 +176,12 @@ public abstract class BaseHasResource implements IBaseResourceEntity {
myHasTags = theHasTags; myHasTags = theHasTags;
} }
static Date cloneDate(Date theDate) {
Date retVal = theDate;
if (retVal != null) {
retVal = new Date(retVal.getTime());
}
return retVal;
}
} }

View File

@ -15,6 +15,7 @@ import org.hl7.fhir.utilities.validation.ValidationMessage.IssueSeverity;
import java.io.InputStream; import java.io.InputStream;
import java.io.InputStreamReader; import java.io.InputStreamReader;
import java.nio.charset.StandardCharsets;
import java.util.*; import java.util.*;
import static org.apache.commons.lang3.StringUtils.isNotBlank; import static org.apache.commons.lang3.StringUtils.isNotBlank;
@ -161,7 +162,7 @@ public class DefaultProfileValidationSupport implements IValidationSupport {
InputStreamReader reader = null; InputStreamReader reader = null;
if (inputStream != null) { if (inputStream != null) {
try { try {
reader = new InputStreamReader(inputStream, Charsets.UTF_8); reader = new InputStreamReader(inputStream, StandardCharsets.UTF_8);
Bundle bundle = theContext.newXmlParser().parseResource(Bundle.class, reader); Bundle bundle = theContext.newXmlParser().parseResource(Bundle.class, reader);
for (BundleEntryComponent next : bundle.getEntry()) { for (BundleEntryComponent next : bundle.getEntry()) {
@ -194,7 +195,7 @@ public class DefaultProfileValidationSupport implements IValidationSupport {
ourLog.info("Loading structure definitions from classpath: {}", theClasspath); ourLog.info("Loading structure definitions from classpath: {}", theClasspath);
InputStream valuesetText = DefaultProfileValidationSupport.class.getResourceAsStream(theClasspath); InputStream valuesetText = DefaultProfileValidationSupport.class.getResourceAsStream(theClasspath);
if (valuesetText != null) { 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); Bundle bundle = theContext.newXmlParser().parseResource(Bundle.class, reader);
for (BundleEntryComponent next : bundle.getEntry()) { for (BundleEntryComponent next : bundle.getEntry()) {

View File

@ -270,6 +270,11 @@
The <![CDATA[<code>_summary</code>]]> element was not always respected when encoding The <![CDATA[<code>_summary</code>]]> element was not always respected when encoding
JSON resources. JSON resources.
</action> </action>
<action type="change">
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.
</action>
<action type="add"> <action type="add">
Added a new Pointcut STORAGE_PRESTORAGE_EXPUNGE_EVERYTHING that is called at the start of Added a new Pointcut STORAGE_PRESTORAGE_EXPUNGE_EVERYTHING that is called at the start of
the expungeEverything operation. the expungeEverything operation.