From 66c2b456de72c62aae78bbb9e07fc1fdfa597459 Mon Sep 17 00:00:00 2001 From: Tadgh Date: Mon, 22 Feb 2021 22:47:08 -0500 Subject: [PATCH] Add more tests --- .../GroupBulkExportJobParametersBuilder.java | 8 +++ .../jpa/bulk/job/GroupBulkItemReader.java | 31 +++++++---- .../jpa/bulk/BulkDataExportSvcImplR4Test.java | 54 ++++++++++++++++--- ...rResourceDaoR4LegacySearchBuilderTest.java | 28 ++++++++++ .../jpa/dao/r4/SearchParameterMapTest.java | 10 ++++ 5 files changed, 114 insertions(+), 17 deletions(-) create mode 100644 hapi-fhir-jpaserver-base/src/main/java/ca/uhn/fhir/jpa/bulk/job/GroupBulkExportJobParametersBuilder.java diff --git a/hapi-fhir-jpaserver-base/src/main/java/ca/uhn/fhir/jpa/bulk/job/GroupBulkExportJobParametersBuilder.java b/hapi-fhir-jpaserver-base/src/main/java/ca/uhn/fhir/jpa/bulk/job/GroupBulkExportJobParametersBuilder.java new file mode 100644 index 00000000000..47da5d2f119 --- /dev/null +++ b/hapi-fhir-jpaserver-base/src/main/java/ca/uhn/fhir/jpa/bulk/job/GroupBulkExportJobParametersBuilder.java @@ -0,0 +1,8 @@ +package ca.uhn.fhir.jpa.bulk.job; + +public class GroupBulkExportJobParametersBuilder extends BulkExportJobParametersBuilder { + public GroupBulkExportJobParametersBuilder setGroupId(String theGroupId) { + this.addString("groupId", theGroupId); + return this; + } +} diff --git a/hapi-fhir-jpaserver-base/src/main/java/ca/uhn/fhir/jpa/bulk/job/GroupBulkItemReader.java b/hapi-fhir-jpaserver-base/src/main/java/ca/uhn/fhir/jpa/bulk/job/GroupBulkItemReader.java index 6d12a1f4c13..dc9314dd798 100644 --- a/hapi-fhir-jpaserver-base/src/main/java/ca/uhn/fhir/jpa/bulk/job/GroupBulkItemReader.java +++ b/hapi-fhir-jpaserver-base/src/main/java/ca/uhn/fhir/jpa/bulk/job/GroupBulkItemReader.java @@ -31,18 +31,25 @@ import ca.uhn.fhir.jpa.dao.ISearchBuilder; import ca.uhn.fhir.jpa.dao.SearchBuilderFactory; import ca.uhn.fhir.jpa.dao.data.IBulkExportJobDao; import ca.uhn.fhir.jpa.entity.BulkExportJobEntity; +import ca.uhn.fhir.jpa.entity.Search; import ca.uhn.fhir.jpa.model.search.SearchRuntimeDetails; import ca.uhn.fhir.jpa.model.util.JpaConstants; import ca.uhn.fhir.jpa.searchparam.MatchUrlService; import ca.uhn.fhir.jpa.searchparam.SearchParameterMap; +import ca.uhn.fhir.model.api.Include; import ca.uhn.fhir.model.primitive.IdDt; import ca.uhn.fhir.rest.api.server.storage.ResourcePersistentId; import ca.uhn.fhir.rest.param.DateRangeParam; +import ca.uhn.fhir.rest.param.HasParam; +import ca.uhn.fhir.rest.param.ReferenceOrListParam; +import ca.uhn.fhir.rest.param.ReferenceParam; +import ca.uhn.fhir.rest.param.StringOrListParam; import ca.uhn.fhir.util.FhirTerser; import ca.uhn.fhir.util.UrlUtil; -import org.hl7.fhir.instance.model.api.IBase; import org.hl7.fhir.instance.model.api.IBaseReference; import org.hl7.fhir.instance.model.api.IBaseResource; +import org.hl7.fhir.r4.model.Immunization; +import org.hl7.fhir.r4.model.Patient; import org.slf4j.Logger; import org.springframework.batch.item.ItemReader; import org.springframework.beans.factory.annotation.Autowired; @@ -80,12 +87,12 @@ public class GroupBulkItemReader implements ItemReader getGroupMembers() { + private List getGroupMemberIds() { IFhirResourceDao group = myDaoRegistry.getResourceDao("Group"); IBaseResource read = group.read(new IdDt(myGroupId)); FhirTerser fhirTerser = myContext.newTerser(); List values = fhirTerser.getValues(read, "Group.member", IBaseReference.class); - return values.stream().map(theIBaseReference -> theIBaseReference.getReferenceElement().getIdPartAsLong()).collect(Collectors.toList()); + return values.stream().map(theIBaseReference -> theIBaseReference.getReferenceElement().getValue()).collect(Collectors.toList()); } private void loadResourcePids() { @@ -97,22 +104,26 @@ public class GroupBulkItemReader implements ItemReader dao = myDaoRegistry.getResourceDao(myResourceType); + IFhirResourceDao dao = myDaoRegistry.getResourceDao("Patient"); ourLog.info("Bulk export assembling export of type {} for job {}", myResourceType, myJobUUID); - RuntimeResourceDefinition def = myContext.getResourceDefinition(myResourceType); + RuntimeResourceDefinition def = myContext.getResourceDefinition("Patient"); Class nextTypeClass = def.getImplementingClass(); ISearchBuilder sb = mySearchBuilderFactory.newSearchBuilder(dao, myResourceType, nextTypeClass); - SearchParameterMap map = createSearchParameterMapFromTypeFilter(jobEntity, def); + SearchParameterMap spm = new SearchParameterMap(); + myGroupId = "21"; + spm.add("_has", new HasParam("Group", "member", "_id", myGroupId)); + spm.addRevInclude(new Include("Immunization:patient").toLocked()); + +// SearchParameterMap map = createSearchParameterMapFromTypeFilter(jobEntity, def); if (jobEntity.getSince() != null) { - map.setLastUpdated(new DateRangeParam(jobEntity.getSince(), null)); + spm.setLastUpdated(new DateRangeParam(jobEntity.getSince(), null)); } - - map.setLoadSynchronous(true); - IResultIterator myResultIterator = sb.createQuery(map, new SearchRuntimeDetails(null, myJobUUID), null, RequestPartitionId.allPartitions()); + spm.setLoadSynchronous(true); + IResultIterator myResultIterator = sb.createQuery(spm, new SearchRuntimeDetails(null, myJobUUID), null, RequestPartitionId.allPartitions()); List myReadPids = new ArrayList<>(); while (myResultIterator.hasNext()) { myReadPids.add(myResultIterator.next()); diff --git a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/bulk/BulkDataExportSvcImplR4Test.java b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/bulk/BulkDataExportSvcImplR4Test.java index b9e2ba48ba2..3827f331990 100644 --- a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/bulk/BulkDataExportSvcImplR4Test.java +++ b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/bulk/BulkDataExportSvcImplR4Test.java @@ -7,6 +7,7 @@ import ca.uhn.fhir.jpa.bulk.api.BulkDataExportOptions; import ca.uhn.fhir.jpa.bulk.api.GroupBulkDataExportOptions; import ca.uhn.fhir.jpa.bulk.api.IBulkDataExportSvc; import ca.uhn.fhir.jpa.bulk.job.BulkExportJobParametersBuilder; +import ca.uhn.fhir.jpa.bulk.job.GroupBulkExportJobParametersBuilder; import ca.uhn.fhir.jpa.bulk.model.BulkJobStatusEnum; import ca.uhn.fhir.jpa.dao.data.IBulkExportCollectionDao; import ca.uhn.fhir.jpa.dao.data.IBulkExportCollectionFileDao; @@ -15,7 +16,12 @@ import ca.uhn.fhir.jpa.dao.r4.BaseJpaR4Test; import ca.uhn.fhir.jpa.entity.BulkExportCollectionEntity; import ca.uhn.fhir.jpa.entity.BulkExportCollectionFileEntity; import ca.uhn.fhir.jpa.entity.BulkExportJobEntity; +import ca.uhn.fhir.jpa.searchparam.SearchParameterMap; +import ca.uhn.fhir.model.api.Include; import ca.uhn.fhir.rest.api.Constants; +import ca.uhn.fhir.rest.api.server.IBundleProvider; +import ca.uhn.fhir.rest.param.HasOrListParam; +import ca.uhn.fhir.rest.param.HasParam; import ca.uhn.fhir.rest.server.exceptions.InvalidRequestException; import ca.uhn.fhir.util.UrlUtil; import com.google.common.base.Charsets; @@ -24,8 +30,10 @@ import org.apache.commons.lang3.time.DateUtils; import org.hamcrest.Matchers; import org.hl7.fhir.instance.model.api.IIdType; import org.hl7.fhir.r4.model.Binary; +import org.hl7.fhir.r4.model.CodeableConcept; import org.hl7.fhir.r4.model.Enumerations; import org.hl7.fhir.r4.model.Group; +import org.hl7.fhir.r4.model.Immunization; import org.hl7.fhir.r4.model.InstantType; import org.hl7.fhir.r4.model.Observation; import org.hl7.fhir.r4.model.Patient; @@ -82,7 +90,11 @@ public class BulkDataExportSvcImplR4Test extends BaseJpaR4Test { @Qualifier("bulkExportJob") private Job myBulkJob; - private String myPatientGroupIp; + @Autowired + @Qualifier("groupBulkExportJob") + private Job myGroupBulkJob; + + private IIdType myPatientGroupId; @Test public void testPurgeExpiredJobs() { @@ -507,15 +519,29 @@ public class BulkDataExportSvcImplR4Test extends BaseJpaR4Test { public void testGroupBatchJobWorks() throws Exception { createResources(); + + // Create a bulk job - IBulkDataExportSvc.JobInfo jobDetails = myBulkDataExportSvc.submitJob(new GroupBulkDataExportOptions(null, Sets.newHashSet("Patient", "Observation"), null, null, myPatientGroupIp)); + IBulkDataExportSvc.JobInfo jobDetails = myBulkDataExportSvc.submitJob(new GroupBulkDataExportOptions(null, Sets.newHashSet("Immunization"), null, null, myPatientGroupId, true)); + + + SearchParameterMap spm = new SearchParameterMap(); + spm.setCount(100); + String tempGroupId = myPatientGroupId.toUnqualifiedVersionless().toString(); + spm.add("_has", new HasOrListParam().add(new HasParam("Group", "member", "_id", "Group/21"))); + spm.addRevInclude(new Include("Immunization:patient")); + spm.setLoadSynchronous(true); + IBundleProvider search = myPatientDao.search(spm); //Add the UUID to the job - BulkExportJobParametersBuilder paramBuilder = new BulkExportJobParametersBuilder() - .setJobUUID(jobDetails.getJobId()) - .setReadChunkSize(10L); + GroupBulkExportJobParametersBuilder paramBuilder = new GroupBulkExportJobParametersBuilder(); + paramBuilder.setGroupId(myPatientGroupId.getValue()); + paramBuilder.setJobUUID(jobDetails.getJobId()); + paramBuilder.setReadChunkSize(10L); - JobExecution jobExecution = myBatchJobSubmitter.runJob(myBulkJob, paramBuilder.toJobParameters()); + GroupBulkExportJobParametersBuilder myBulkExportParametersBuilder = new GroupBulkExportJobParametersBuilder(); + myBulkExportParametersBuilder.setGroupId(myPatientGroupId.getValue()); + JobExecution jobExecution = myBatchJobSubmitter.runJob(myGroupBulkJob, paramBuilder.toJobParameters()); awaitJobCompletion(jobExecution); IBulkDataExportSvc.JobInfo jobInfo = myBulkDataExportSvc.getJobInfoOrThrowResourceNotFound(jobDetails.getJobId()); @@ -561,8 +587,22 @@ public class BulkDataExportSvcImplR4Test extends BaseJpaR4Test { obs.setStatus(Observation.ObservationStatus.FINAL); obs.getSubject().setReference(patId.getValue()); myObservationDao.update(obs); + + Immunization immunization = new Immunization(); + immunization.setPatient(new Reference(patId)); + if (i % 2 == 0) { + CodeableConcept cc = new CodeableConcept(); + cc.addCoding().setSystem("vaccines").setCode("Flu"); + immunization.setVaccineCode(cc); + } else { + CodeableConcept cc = new CodeableConcept(); + cc.addCoding().setSystem("vaccines").setCode("COVID-19"); + immunization.setVaccineCode(cc); + } + myImmunizationDao.create(immunization); } - myPatientGroupIp = myGroupDao.create(group).getId().getValue(); + myPatientGroupId = myGroupDao.create(group).getId(); + } } diff --git a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/r4/FhirResourceDaoR4LegacySearchBuilderTest.java b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/r4/FhirResourceDaoR4LegacySearchBuilderTest.java index bcd03a8640d..8613fd97160 100644 --- a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/r4/FhirResourceDaoR4LegacySearchBuilderTest.java +++ b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/r4/FhirResourceDaoR4LegacySearchBuilderTest.java @@ -5,6 +5,7 @@ import ca.uhn.fhir.interceptor.api.HookParams; import ca.uhn.fhir.interceptor.api.IAnonymousInterceptor; import ca.uhn.fhir.interceptor.api.Pointcut; import ca.uhn.fhir.jpa.api.config.DaoConfig; +import ca.uhn.fhir.jpa.api.model.DaoMethodOutcome; import ca.uhn.fhir.jpa.entity.Search; import ca.uhn.fhir.jpa.model.config.PartitionSettings; import ca.uhn.fhir.jpa.model.entity.ModelConfig; @@ -87,6 +88,7 @@ import org.hl7.fhir.r4.model.Enumerations.AdministrativeGender; import org.hl7.fhir.r4.model.EpisodeOfCare; import org.hl7.fhir.r4.model.Group; import org.hl7.fhir.r4.model.IdType; +import org.hl7.fhir.r4.model.Immunization; import org.hl7.fhir.r4.model.InstantType; import org.hl7.fhir.r4.model.IntegerType; import org.hl7.fhir.r4.model.Location; @@ -268,6 +270,32 @@ public class FhirResourceDaoR4LegacySearchBuilderTest extends BaseJpaR4Test { assertThat(ids, hasItems(patientId)); } + @Test + public void testPatientHasGroupImmunization(){ + + Patient patient = new Patient(); + String patientId = myPatientDao.create(patient).getId().toUnqualifiedVersionless().getValue(); + + Group group = new Group(); + group.addMember().setEntity(new Reference(patientId)); + Long daoMethodOutcome = myGroupDao.create(group).getId().getIdPartAsLong(); + + Immunization immunization = new Immunization(); + immunization.setPatient(new Reference(patientId)); + String immunizationId = myImmunizationDao.create(immunization).getId().toUnqualifiedVersionless().getValue(); + + String criteria = "?_has:Group:member:_id="+ daoMethodOutcome + "&_revinclude=Immunization:patient"; + //TODO GGG the matchUrlService _doesnt translate rev includes! + SearchParameterMap searchParameterMap = myMatchUrlService.translateMatchUrl(criteria, myFhirCtx.getResourceDefinition(Patient.class)); + searchParameterMap.addRevInclude(new Include("Immunization:patient").toLocked()); + searchParameterMap.setLoadSynchronous(true); + + IBundleProvider search = myPatientDao.search(searchParameterMap); + List strings = toUnqualifiedVersionlessIdValues(search); + assertThat(strings, hasItems(patientId, immunizationId)); + + } + @Test public void testHasConditionOr() { Patient patient = new Patient(); diff --git a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/r4/SearchParameterMapTest.java b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/r4/SearchParameterMapTest.java index 2195260620a..2bdcc6f4a4d 100644 --- a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/r4/SearchParameterMapTest.java +++ b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/dao/r4/SearchParameterMapTest.java @@ -3,6 +3,7 @@ package ca.uhn.fhir.jpa.dao.r4; import ca.uhn.fhir.context.FhirContext; import ca.uhn.fhir.context.FhirVersionEnum; import ca.uhn.fhir.jpa.searchparam.SearchParameterMap; +import ca.uhn.fhir.model.api.Include; import ca.uhn.fhir.rest.param.HasParam; import ca.uhn.fhir.test.BaseTest; import org.junit.jupiter.api.Test; @@ -21,4 +22,13 @@ public class SearchParameterMapTest extends BaseTest { assertEquals(criteria, "?_has:Observation:identifier:urn:system|FOO=urn%3Asystem%7CFOO"); } + @Test + public void testGroupToImmunizationHas() { + SearchParameterMap params = new SearchParameterMap(); + params.add("_has", new HasParam("Group", "member", "_id", "1000")); + params.addRevInclude(new Include("Immunization:patient")); + String criteria = params.toNormalizedQueryString(myContext); + assertEquals("?_has:Group:member:_id=1000&_revinclude=Immunization:patient", criteria); + } + }