From bc545f8e3c471c9640fb79b999abe42a3ae98c6c Mon Sep 17 00:00:00 2001 From: James Agnew Date: Thu, 20 Apr 2017 16:11:09 -0400 Subject: [PATCH] Issue #590 - Handle paging requests for AuthorizationInterceptor --- .../auth/AuthorizationInterceptor.java | 3 +- .../server/interceptor/auth/RuleImplOp.java | 1 - .../AuthorizationInterceptorDstu2Test.java | 97 +++++++++++++++++++ src/changes/changes.xml | 6 ++ 4 files changed, 104 insertions(+), 3 deletions(-) diff --git a/hapi-fhir-base/src/main/java/ca/uhn/fhir/rest/server/interceptor/auth/AuthorizationInterceptor.java b/hapi-fhir-base/src/main/java/ca/uhn/fhir/rest/server/interceptor/auth/AuthorizationInterceptor.java index b53baf4dd69..c1b775947c4 100644 --- a/hapi-fhir-base/src/main/java/ca/uhn/fhir/rest/server/interceptor/auth/AuthorizationInterceptor.java +++ b/hapi-fhir-base/src/main/java/ca/uhn/fhir/rest/server/interceptor/auth/AuthorizationInterceptor.java @@ -278,13 +278,12 @@ public class AuthorizationInterceptor extends InterceptorAdapter implements ISer case HISTORY_SYSTEM: case HISTORY_TYPE: case TRANSACTION: + case GET_PAGE: case EXTENDED_OPERATION_SERVER: case EXTENDED_OPERATION_TYPE: case EXTENDED_OPERATION_INSTANCE: { if (theResponseObject != null) { if (theResponseObject instanceof IBaseBundle) { - // IBaseBundle responseBundle = (IBaseBundle) theResponseObject; - // resources = toListOfResources(fhirContext, responseBundle); resources = toListOfResourcesAndExcludeContainer(theResponseObject, fhirContext); } else if (theResponseObject instanceof IBaseParameters) { resources = toListOfResourcesAndExcludeContainer(theResponseObject, fhirContext); diff --git a/hapi-fhir-base/src/main/java/ca/uhn/fhir/rest/server/interceptor/auth/RuleImplOp.java b/hapi-fhir-base/src/main/java/ca/uhn/fhir/rest/server/interceptor/auth/RuleImplOp.java index 0facbab29bb..61bfebdb033 100644 --- a/hapi-fhir-base/src/main/java/ca/uhn/fhir/rest/server/interceptor/auth/RuleImplOp.java +++ b/hapi-fhir-base/src/main/java/ca/uhn/fhir/rest/server/interceptor/auth/RuleImplOp.java @@ -75,7 +75,6 @@ class RuleImplOp extends BaseRule /* implements IAuthRule */ { appliesToResourceId = theInputResourceId; appliesToResourceType = theInputResourceId.getResourceType(); break; - // return new Verdict(PolicyEnum.ALLOW, this); case SEARCH_SYSTEM: case SEARCH_TYPE: case HISTORY_INSTANCE: diff --git a/hapi-fhir-structures-dstu2/src/test/java/ca/uhn/fhir/rest/server/interceptor/auth/AuthorizationInterceptorDstu2Test.java b/hapi-fhir-structures-dstu2/src/test/java/ca/uhn/fhir/rest/server/interceptor/auth/AuthorizationInterceptorDstu2Test.java index 26bdeb791d7..8430c5a2bda 100644 --- a/hapi-fhir-structures-dstu2/src/test/java/ca/uhn/fhir/rest/server/interceptor/auth/AuthorizationInterceptorDstu2Test.java +++ b/hapi-fhir-structures-dstu2/src/test/java/ca/uhn/fhir/rest/server/interceptor/auth/AuthorizationInterceptorDstu2Test.java @@ -1209,6 +1209,102 @@ public class AuthorizationInterceptorDstu2Test { } + @Test + public void testReadPageRight() throws Exception { + ourServlet.registerInterceptor(new AuthorizationInterceptor(PolicyEnum.DENY) { + @Override + public List buildRuleList(RequestDetails theRequestDetails) { + return new RuleBuilder() + .allow("Rule 1").read().resourcesOfType(Patient.class).inCompartment("Patient", new IdDt("Patient/1")) + .build(); + } + }); + + HttpGet httpGet; + HttpResponse status; + String respString; + Bundle respBundle; + + ourReturn = new ArrayList(); + for (int i = 0; i < 10; i++) { + ourReturn.add(createPatient(1)); + } + + ourHitMethod = false; + httpGet = new HttpGet("http://localhost:" + ourPort + "/Patient?_count=5&_format=json"); + status = ourClient.execute(httpGet); + respString = extractResponseAndClose(status); + assertEquals(200, status.getStatusLine().getStatusCode()); + assertTrue(ourHitMethod); + respBundle = ourCtx.newJsonParser().parseResource(Bundle.class, respString); + assertEquals(5, respBundle.getEntry().size()); + assertEquals(10, respBundle.getTotal().intValue()); + assertEquals("Patient/1", respBundle.getEntry().get(0).getResource().getIdElement().toUnqualifiedVersionless().getValue()); + assertNotNull(respBundle.getLink("next")); + + // Load next page + + ourHitMethod = false; + httpGet = new HttpGet(respBundle.getLink("next").getUrl()); + status = ourClient.execute(httpGet); + respString = extractResponseAndClose(status); + assertEquals(200, status.getStatusLine().getStatusCode()); + assertFalse(ourHitMethod); + respBundle = ourCtx.newJsonParser().parseResource(Bundle.class, respString); + assertEquals(5, respBundle.getEntry().size()); + assertEquals(10, respBundle.getTotal().intValue()); + assertEquals("Patient/1", respBundle.getEntry().get(0).getResource().getIdElement().toUnqualifiedVersionless().getValue()); + assertNull(respBundle.getLink("next")); + + } + + @Test + public void testReadPageWrong() throws Exception { + ourServlet.registerInterceptor(new AuthorizationInterceptor(PolicyEnum.DENY) { + @Override + public List buildRuleList(RequestDetails theRequestDetails) { + return new RuleBuilder() + .allow("Rule 1").read().resourcesOfType(Patient.class).inCompartment("Patient", new IdDt("Patient/1")) + .build(); + } + }); + + HttpGet httpGet; + HttpResponse status; + String respString; + Bundle respBundle; + + ourReturn = new ArrayList(); + for (int i = 0; i < 5; i++) { + ourReturn.add(createPatient(1)); + } + for (int i = 0; i < 5; i++) { + ourReturn.add(createPatient(2)); + } + + ourHitMethod = false; + httpGet = new HttpGet("http://localhost:" + ourPort + "/Patient?_count=5&_format=json"); + status = ourClient.execute(httpGet); + respString = extractResponseAndClose(status); + assertEquals(200, status.getStatusLine().getStatusCode()); + assertTrue(ourHitMethod); + respBundle = ourCtx.newJsonParser().parseResource(Bundle.class, respString); + assertEquals(5, respBundle.getEntry().size()); + assertEquals(10, respBundle.getTotal().intValue()); + assertEquals("Patient/1", respBundle.getEntry().get(0).getResource().getIdElement().toUnqualifiedVersionless().getValue()); + assertNotNull(respBundle.getLink("next")); + + // Load next page + + ourHitMethod = false; + httpGet = new HttpGet(respBundle.getLink("next").getUrl()); + status = ourClient.execute(httpGet); + respString = extractResponseAndClose(status); + assertEquals(403, status.getStatusLine().getStatusCode()); + assertFalse(ourHitMethod); + + } + @Test public void testReadByCompartmentWrong() throws Exception { ourServlet.registerInterceptor(new AuthorizationInterceptor(PolicyEnum.DENY) { @@ -1850,6 +1946,7 @@ public class AuthorizationInterceptorDstu2Test { ourServlet.setFhirContext(ourCtx); ourServlet.setResourceProviders(patProvider, obsProv, encProv, cpProv); ourServlet.setPlainProviders(plainProvider); + ourServlet.setPagingProvider(new FifoMemoryPagingProvider(100)); ServletHolder servletHolder = new ServletHolder(ourServlet); proxyHandler.addServletWithMapping(servletHolder, "/*"); ourServer.setHandler(proxyHandler); diff --git a/src/changes/changes.xml b/src/changes/changes.xml index dfeab42c8e2..708ce3d2fe8 100644 --- a/src/changes/changes.xml +++ b/src/changes/changes.xml @@ -6,6 +6,12 @@ HAPI FHIR Changelog + + + AuthorizationInterceptor did not correctly handle paging requests + (e.g. requests for the second page of results for a search operation). + Thanks to Eeva Turkka for reporting! + This release brings the DSTU3 structures up to FHIR R3 (FHIR 3.0.1) definitions. Note that