diff --git a/hapi-fhir-base/src/main/java/ca/uhn/fhir/util/ResourceReferenceInfo.java b/hapi-fhir-base/src/main/java/ca/uhn/fhir/util/ResourceReferenceInfo.java index adac282629e..35e10217f13 100644 --- a/hapi-fhir-base/src/main/java/ca/uhn/fhir/util/ResourceReferenceInfo.java +++ b/hapi-fhir-base/src/main/java/ca/uhn/fhir/util/ResourceReferenceInfo.java @@ -101,11 +101,11 @@ public class ResourceReferenceInfo { if (resourceDef != null) { RuntimeSearchParam searchParamDef = resourceDef.getSearchParam(paramName); if (searchParamDef!=null) { - final String myCompleteName = myOwningResource + "." + myName; + final String completeName = myOwningResource + "." + myName; boolean matched = false; for (String s : searchParamDef.getPathsSplit()) { - if (s.equals(myCompleteName) || - s.startsWith(myCompleteName + ".")) { + if (s.equals(completeName) || + s.startsWith(completeName + ".")) { matched = true; break; } } diff --git a/hapi-fhir-structures-r4/src/test/java/ca/uhn/fhir/rest/server/SearchR4Test.java b/hapi-fhir-structures-r4/src/test/java/ca/uhn/fhir/rest/server/SearchR4Test.java index 73d0a03d23d..2bea53030a5 100644 --- a/hapi-fhir-structures-r4/src/test/java/ca/uhn/fhir/rest/server/SearchR4Test.java +++ b/hapi-fhir-structures-r4/src/test/java/ca/uhn/fhir/rest/server/SearchR4Test.java @@ -1,6 +1,8 @@ package ca.uhn.fhir.rest.server; import ca.uhn.fhir.context.FhirContext; +import ca.uhn.fhir.model.api.Include; +import ca.uhn.fhir.rest.annotation.IncludeParam; import ca.uhn.fhir.rest.annotation.RequiredParam; import ca.uhn.fhir.rest.annotation.Search; import ca.uhn.fhir.rest.api.Constants; @@ -14,6 +16,7 @@ import ca.uhn.fhir.rest.server.exceptions.InvalidRequestException; import ca.uhn.fhir.util.PortUtil; import ca.uhn.fhir.util.TestUtil; import ca.uhn.fhir.util.UrlUtil; +import com.google.common.collect.Lists; import org.apache.commons.io.IOUtils; import org.apache.http.client.ClientProtocolException; import org.apache.http.client.methods.CloseableHttpResponse; @@ -25,10 +28,7 @@ import org.eclipse.jetty.server.Server; import org.eclipse.jetty.servlet.ServletHandler; import org.eclipse.jetty.servlet.ServletHolder; import org.hl7.fhir.instance.model.api.IBaseResource; -import org.hl7.fhir.r4.model.Bundle; -import org.hl7.fhir.r4.model.HumanName; -import org.hl7.fhir.r4.model.OperationOutcome; -import org.hl7.fhir.r4.model.Patient; +import org.hl7.fhir.r4.model.*; import org.junit.AfterClass; import org.junit.Before; import org.junit.BeforeClass; @@ -38,6 +38,7 @@ import java.io.IOException; import java.nio.charset.StandardCharsets; import java.util.ArrayList; import java.util.List; +import java.util.Set; import java.util.concurrent.TimeUnit; import static org.hamcrest.Matchers.containsString; @@ -121,6 +122,43 @@ public class SearchR4Test { } + /** + * See #836 + */ + @Test + public void testIncludeSingleParameter() throws Exception { + HttpGet httpGet; + String linkNext; + Bundle bundle; + String linkSelf; + + // No include specified + httpGet = new HttpGet("http://localhost:" + ourPort + "/MedicationRequest"); + bundle = executeAndReturnBundle(httpGet); + assertEquals(1, bundle.getEntry().size()); + + // * include specified + httpGet = new HttpGet("http://localhost:" + ourPort + "/MedicationRequest?_include=" + UrlUtil.escapeUrlParam("*")); + bundle = executeAndReturnBundle(httpGet); + assertEquals(2, bundle.getEntry().size()); + + // MedicationRequest:medication include specified + httpGet = new HttpGet("http://localhost:" + ourPort + "/MedicationRequest?_include=" + UrlUtil.escapeUrlParam("MedicationRequest:medication")); + bundle = executeAndReturnBundle(httpGet); + assertEquals(2, bundle.getEntry().size()); + + } + + private Bundle executeAndReturnBundle(HttpGet theHttpGet) throws IOException { + Bundle bundle; + try (CloseableHttpResponse status = ourClient.execute(theHttpGet)) { + String responseContent = IOUtils.toString(status.getEntity().getContent(), StandardCharsets.UTF_8); + assertEquals(200, status.getStatusLine().getStatusCode()); + bundle = ourCtx.newJsonParser().parseResource(Bundle.class, responseContent); + } + return bundle; + } + @Test public void testPagingPreservesEncodingApplicationJsonFhir() throws Exception { HttpGet httpGet; @@ -368,13 +406,14 @@ public class SearchR4Test { ourServer = new Server(ourPort); DummyPatientResourceProvider patientProvider = new DummyPatientResourceProvider(); + DummyMedicationRequestResourceProvider medRequestProvider = new DummyMedicationRequestResourceProvider(); ServletHandler proxyHandler = new ServletHandler(); RestfulServer servlet = new RestfulServer(ourCtx); servlet.setDefaultResponseEncoding(EncodingEnum.JSON); servlet.setPagingProvider(new FifoMemoryPagingProvider(10)); - servlet.setResourceProviders(patientProvider); + servlet.setResourceProviders(patientProvider, medRequestProvider); ServletHolder servletHolder = new ServletHolder(servlet); proxyHandler.addServletWithMapping(servletHolder, "/*"); ourServer.setHandler(proxyHandler); @@ -414,4 +453,30 @@ public class SearchR4Test { } + public static class DummyMedicationRequestResourceProvider implements IResourceProvider { + + @Override + public Class getResourceType() { + return MedicationRequest.class; + } + + @SuppressWarnings("rawtypes") + @Search() + public List search( + @IncludeParam Set theIncludes + ) { + MedicationRequest mr = new MedicationRequest(); + mr.setId("1"); + mr.setStatus(MedicationRequest.MedicationRequestStatus.ACTIVE); + + Medication m = new Medication(); + m.setId("2"); + m.setStatus(Medication.MedicationStatus.ENTEREDINERROR); + mr.setMedication(new Reference(m)); + + return Lists.newArrayList(mr); + } + + } + } diff --git a/pom.xml b/pom.xml index 603e2c7f87c..88cae6c251d 100644 --- a/pom.xml +++ b/pom.xml @@ -436,6 +436,9 @@ dgileadi David Gileadi + + RuthAlk + diff --git a/src/changes/changes.xml b/src/changes/changes.xml index af05d60ce0e..f72a219effb 100644 --- a/src/changes/changes.xml +++ b/src/changes/changes.xml @@ -201,6 +201,11 @@ returned to the user. This has been enhanced to also include the message from the underlying exception. + + A bug in the plain server was fixed that prevented some includes from + correctly causing their targets to be included in the response bundle. + Thanks to GitHub user @RuthAlk for the pull request! +