Add client interceptor which adds bearer tokens for OAUTH2
This commit is contained in:
parent
5c0ccaab9a
commit
a610c1cb38
|
@ -5,6 +5,7 @@ import ca.uhn.fhir.rest.client.IGenericClient;
|
||||||
import ca.uhn.fhir.rest.client.IRestfulClientFactory;
|
import ca.uhn.fhir.rest.client.IRestfulClientFactory;
|
||||||
import ca.uhn.fhir.rest.client.api.IBasicClient;
|
import ca.uhn.fhir.rest.client.api.IBasicClient;
|
||||||
import ca.uhn.fhir.rest.client.interceptor.BasicAuthInterceptor;
|
import ca.uhn.fhir.rest.client.interceptor.BasicAuthInterceptor;
|
||||||
|
import ca.uhn.fhir.rest.client.interceptor.BearerTokenAuthInterceptor;
|
||||||
import ca.uhn.fhir.rest.client.interceptor.LoggingInterceptor;
|
import ca.uhn.fhir.rest.client.interceptor.LoggingInterceptor;
|
||||||
import ca.uhn.fhir.rest.server.EncodingEnum;
|
import ca.uhn.fhir.rest.server.EncodingEnum;
|
||||||
|
|
||||||
|
@ -45,6 +46,27 @@ public class ClientExamples {
|
||||||
// END SNIPPET: security
|
// END SNIPPET: security
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@SuppressWarnings("unused")
|
||||||
|
public void createSecurityBearer() {
|
||||||
|
// START SNIPPET: securityBearer
|
||||||
|
// Create a context and get the client factory so it can be configured
|
||||||
|
FhirContext ctx = new FhirContext();
|
||||||
|
IRestfulClientFactory clientFactory = ctx.getRestfulClientFactory();
|
||||||
|
|
||||||
|
// In reality the token would have come from an authorization server
|
||||||
|
String token = "3w03fj.r3r3t";
|
||||||
|
|
||||||
|
BearerTokenAuthInterceptor authInterceptor = new BearerTokenAuthInterceptor(token);
|
||||||
|
|
||||||
|
// Register the interceptor with your client (either style)
|
||||||
|
IPatientClient annotationClient = ctx.newRestfulClient(IPatientClient.class, "http://localhost:9999/fhir");
|
||||||
|
annotationClient.registerInterceptor(authInterceptor);
|
||||||
|
|
||||||
|
IGenericClient genericClient = ctx.newRestfulGenericClient("http://localhost:9999/fhir");
|
||||||
|
annotationClient.registerInterceptor(authInterceptor);
|
||||||
|
// END SNIPPET: securityBearer
|
||||||
|
}
|
||||||
|
|
||||||
@SuppressWarnings("unused")
|
@SuppressWarnings("unused")
|
||||||
public void createLogging() {
|
public void createLogging() {
|
||||||
{
|
{
|
||||||
|
|
|
@ -0,0 +1,63 @@
|
||||||
|
package ca.uhn.fhir.rest.client.interceptor;
|
||||||
|
|
||||||
|
/*
|
||||||
|
* #%L
|
||||||
|
* HAPI FHIR - Core Library
|
||||||
|
* %%
|
||||||
|
* Copyright (C) 2014 University Health Network
|
||||||
|
* %%
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
* #L%
|
||||||
|
*/
|
||||||
|
|
||||||
|
import java.io.IOException;
|
||||||
|
|
||||||
|
import org.apache.commons.lang3.Validate;
|
||||||
|
import org.apache.http.HttpResponse;
|
||||||
|
import org.apache.http.client.methods.HttpRequestBase;
|
||||||
|
|
||||||
|
import ca.uhn.fhir.rest.client.IClientInterceptor;
|
||||||
|
import ca.uhn.fhir.rest.server.Constants;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* HTTP interceptor to be used for adding HTTP Authorization using "bearer tokens" to requests. Bearer tokens are used for protocols such as OAUTH2 (see the <a
|
||||||
|
* href="http://tools.ietf.org/html/rfc6750">RFC 6750</a> specification on bearer token usage for more information).
|
||||||
|
* <p>
|
||||||
|
* This interceptor adds a header resembling the following:<br/>
|
||||||
|
* <code>Authorization: Bearer dsfu9sd90fwp34.erw0-reu</code><br/>
|
||||||
|
* where the token portion (at the end of the header) is supplied by the invoking code.
|
||||||
|
* </p>
|
||||||
|
* <p>
|
||||||
|
* See the <a href="http://hl7api.sourceforge.net/hapi-fhir/doc_rest_client.html#HTTP_Basic_Authorization">HAPI Documentation</a> for information on how to use this class.
|
||||||
|
* </p>
|
||||||
|
*/
|
||||||
|
public class BearerTokenAuthInterceptor implements IClientInterceptor {
|
||||||
|
|
||||||
|
private String myToken;
|
||||||
|
|
||||||
|
public BearerTokenAuthInterceptor(String theToken) {
|
||||||
|
Validate.notNull("theToken must not be null");
|
||||||
|
myToken = theToken;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void interceptRequest(HttpRequestBase theRequest) {
|
||||||
|
theRequest.addHeader(Constants.HEADER_AUTHORIZATION, (Constants.HEADER_AUTHORIZATION_VALPREFIX_BEARER + myToken));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void interceptResponse(HttpResponse theResponse) throws IOException {
|
||||||
|
// nothing
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -48,6 +48,8 @@ public class Constants {
|
||||||
public static final String HEADER_ACCEPT_ENCODING = "Accept-Encoding";
|
public static final String HEADER_ACCEPT_ENCODING = "Accept-Encoding";
|
||||||
public static final String HEADER_AUTHORIZATION = "Authorization";
|
public static final String HEADER_AUTHORIZATION = "Authorization";
|
||||||
public static final String HEADER_CATEGORY = "Category";
|
public static final String HEADER_CATEGORY = "Category";
|
||||||
|
public static final String HEADER_AUTHORIZATION_VALPREFIX_BASIC = "Basic ";
|
||||||
|
public static final String HEADER_AUTHORIZATION_VALPREFIX_BEARER = "Bearer ";
|
||||||
public static final String HEADER_CATEGORY_LC = HEADER_CATEGORY.toLowerCase();
|
public static final String HEADER_CATEGORY_LC = HEADER_CATEGORY.toLowerCase();
|
||||||
public static final String HEADER_CONTENT_DISPOSITION = "Content-Disposition";
|
public static final String HEADER_CONTENT_DISPOSITION = "Content-Disposition";
|
||||||
public static final String HEADER_CONTENT_ENCODING = "Content-Encoding";
|
public static final String HEADER_CONTENT_ENCODING = "Content-Encoding";
|
||||||
|
|
|
@ -25,7 +25,7 @@
|
||||||
The following section shows some sample interceptors which may be used.
|
The following section shows some sample interceptors which may be used.
|
||||||
</p>
|
</p>
|
||||||
|
|
||||||
<subsection name="HTTP Basic Authorization">
|
<subsection name="Security: HTTP Basic Authorization">
|
||||||
|
|
||||||
<p>
|
<p>
|
||||||
The following example shows how to configure your client to
|
The following example shows how to configure your client to
|
||||||
|
@ -39,14 +39,29 @@
|
||||||
|
|
||||||
</subsection>
|
</subsection>
|
||||||
|
|
||||||
<a name="req_resp_logging"/>
|
<subsection name="Security: HTTP Bearer Token Authorization">
|
||||||
<subsection name="Logging Requests and Responses">
|
|
||||||
|
|
||||||
<p>
|
<p>
|
||||||
An interceptor is provided with HAPI FHIR which can be used to
|
The following example shows how to configure your client to
|
||||||
log every transaction. The interceptor can be configured to be extremely
|
inject a bearer token authorization header into every request. This
|
||||||
|
is used to satisfy servers which are protected using OAUTH2.
|
||||||
|
</p>
|
||||||
|
|
||||||
|
<macro name="snippet">
|
||||||
|
<param name="id" value="securityBearer" />
|
||||||
|
<param name="file" value="examples/src/main/java/example/ClientExamples.java" />
|
||||||
|
</macro>
|
||||||
|
|
||||||
|
</subsection>
|
||||||
|
|
||||||
|
<a name="req_resp_logging"/>
|
||||||
|
<subsection name="Logging: Log Requests and Responses">
|
||||||
|
|
||||||
|
<p>
|
||||||
|
The <code>LoggingInterceptor</code> can be used to
|
||||||
|
log every transaction. The interceptor is flexible and can be configured to be extremely
|
||||||
verbose (logging entire transactions including HTTP headers and payload bodies)
|
verbose (logging entire transactions including HTTP headers and payload bodies)
|
||||||
or simply to log request URLs.
|
or simply to log request URLs, or some combination in between.
|
||||||
</p>
|
</p>
|
||||||
|
|
||||||
<macro name="snippet">
|
<macro name="snippet">
|
||||||
|
|
|
@ -0,0 +1,87 @@
|
||||||
|
package ca.uhn.fhir.rest.client;
|
||||||
|
|
||||||
|
import static org.junit.Assert.assertEquals;
|
||||||
|
import static org.mockito.Mockito.mock;
|
||||||
|
import static org.mockito.Mockito.when;
|
||||||
|
|
||||||
|
import java.io.StringReader;
|
||||||
|
import java.nio.charset.Charset;
|
||||||
|
|
||||||
|
import org.apache.commons.io.input.ReaderInputStream;
|
||||||
|
import org.apache.http.Header;
|
||||||
|
import org.apache.http.HttpResponse;
|
||||||
|
import org.apache.http.ProtocolVersion;
|
||||||
|
import org.apache.http.client.HttpClient;
|
||||||
|
import org.apache.http.client.methods.HttpUriRequest;
|
||||||
|
import org.apache.http.message.BasicHeader;
|
||||||
|
import org.apache.http.message.BasicStatusLine;
|
||||||
|
import org.junit.Before;
|
||||||
|
import org.junit.BeforeClass;
|
||||||
|
import org.junit.Test;
|
||||||
|
import org.mockito.ArgumentCaptor;
|
||||||
|
import org.mockito.internal.stubbing.defaultanswers.ReturnsDeepStubs;
|
||||||
|
|
||||||
|
import ca.uhn.fhir.context.FhirContext;
|
||||||
|
import ca.uhn.fhir.model.primitive.IdDt;
|
||||||
|
import ca.uhn.fhir.rest.client.interceptor.BasicAuthInterceptor;
|
||||||
|
import ca.uhn.fhir.rest.server.Constants;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Created by dsotnikov on 2/25/2014.
|
||||||
|
*/
|
||||||
|
public class BasicAuthInterceptorTest {
|
||||||
|
|
||||||
|
private static FhirContext ourCtx;
|
||||||
|
private HttpClient myHttpClient;
|
||||||
|
private HttpResponse myHttpResponse;
|
||||||
|
|
||||||
|
@Before
|
||||||
|
public void before() {
|
||||||
|
myHttpClient = mock(HttpClient.class, new ReturnsDeepStubs());
|
||||||
|
ourCtx.getRestfulClientFactory().setHttpClient(myHttpClient);
|
||||||
|
|
||||||
|
myHttpResponse = mock(HttpResponse.class, new ReturnsDeepStubs());
|
||||||
|
}
|
||||||
|
|
||||||
|
private String crerateMsg() {
|
||||||
|
//@formatter:off
|
||||||
|
String msg = "<Patient xmlns=\"http://hl7.org/fhir\">"
|
||||||
|
+ "<text><status value=\"generated\" /><div xmlns=\"http://www.w3.org/1999/xhtml\">John Cardinal: 444333333 </div></text>"
|
||||||
|
+ "<identifier><label value=\"SSN\" /><system value=\"http://orionhealth.com/mrn\" /><value value=\"PRP1660\" /></identifier>"
|
||||||
|
+ "<name><use value=\"official\" /><family value=\"Cardinal\" /><given value=\"John\" /></name>"
|
||||||
|
+ "<name><family value=\"Kramer\" /><given value=\"Doe\" /></name>"
|
||||||
|
+ "<telecom><system value=\"phone\" /><value value=\"555-555-2004\" /><use value=\"work\" /></telecom>"
|
||||||
|
+ "<gender><coding><system value=\"http://hl7.org/fhir/v3/AdministrativeGender\" /><code value=\"M\" /></coding></gender>"
|
||||||
|
+ "<address><use value=\"home\" /><line value=\"2222 Home Street\" /></address><active value=\"true\" />"
|
||||||
|
+ "</Patient>";
|
||||||
|
//@formatter:on
|
||||||
|
return msg;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void testRequest() throws Exception {
|
||||||
|
String msg = crerateMsg();
|
||||||
|
|
||||||
|
ArgumentCaptor<HttpUriRequest> capt = ArgumentCaptor.forClass(HttpUriRequest.class);
|
||||||
|
when(myHttpClient.execute(capt.capture())).thenReturn(myHttpResponse);
|
||||||
|
when(myHttpResponse.getStatusLine()).thenReturn(new BasicStatusLine(new ProtocolVersion("HTTP", 1, 1), 200, "OK"));
|
||||||
|
Header[] headers = new Header[] {};
|
||||||
|
|
||||||
|
when(myHttpResponse.getAllHeaders()).thenReturn(headers);
|
||||||
|
when(myHttpResponse.getEntity().getContentType()).thenReturn(new BasicHeader("content-type", Constants.CT_FHIR_XML + "; charset=UTF-8"));
|
||||||
|
when(myHttpResponse.getEntity().getContent()).thenReturn(new ReaderInputStream(new StringReader(msg), Charset.forName("UTF-8")));
|
||||||
|
|
||||||
|
ITestClient client = ourCtx.newRestfulClient(ITestClient.class, "http://foo");
|
||||||
|
client.registerInterceptor(new BasicAuthInterceptor("myuser", "mypass"));
|
||||||
|
client.getPatientById(new IdDt("111"));
|
||||||
|
|
||||||
|
HttpUriRequest req = capt.getValue();
|
||||||
|
assertEquals("Basic bXl1c2VyOm15cGFzcw==", req.getFirstHeader("Authorization").getValue());
|
||||||
|
}
|
||||||
|
|
||||||
|
@BeforeClass
|
||||||
|
public static void beforeClass() {
|
||||||
|
ourCtx = new FhirContext();
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -0,0 +1,87 @@
|
||||||
|
package ca.uhn.fhir.rest.client;
|
||||||
|
|
||||||
|
import static org.junit.Assert.assertEquals;
|
||||||
|
import static org.mockito.Mockito.mock;
|
||||||
|
import static org.mockito.Mockito.when;
|
||||||
|
|
||||||
|
import java.io.StringReader;
|
||||||
|
import java.nio.charset.Charset;
|
||||||
|
|
||||||
|
import org.apache.commons.io.input.ReaderInputStream;
|
||||||
|
import org.apache.http.Header;
|
||||||
|
import org.apache.http.HttpResponse;
|
||||||
|
import org.apache.http.ProtocolVersion;
|
||||||
|
import org.apache.http.client.HttpClient;
|
||||||
|
import org.apache.http.client.methods.HttpUriRequest;
|
||||||
|
import org.apache.http.message.BasicHeader;
|
||||||
|
import org.apache.http.message.BasicStatusLine;
|
||||||
|
import org.junit.Before;
|
||||||
|
import org.junit.BeforeClass;
|
||||||
|
import org.junit.Test;
|
||||||
|
import org.mockito.ArgumentCaptor;
|
||||||
|
import org.mockito.internal.stubbing.defaultanswers.ReturnsDeepStubs;
|
||||||
|
|
||||||
|
import ca.uhn.fhir.context.FhirContext;
|
||||||
|
import ca.uhn.fhir.model.primitive.IdDt;
|
||||||
|
import ca.uhn.fhir.rest.client.interceptor.BearerTokenAuthInterceptor;
|
||||||
|
import ca.uhn.fhir.rest.server.Constants;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Created by dsotnikov on 2/25/2014.
|
||||||
|
*/
|
||||||
|
public class BearerTokenAuthInterceptorTest {
|
||||||
|
|
||||||
|
private static FhirContext ourCtx;
|
||||||
|
private HttpClient myHttpClient;
|
||||||
|
private HttpResponse myHttpResponse;
|
||||||
|
|
||||||
|
@Before
|
||||||
|
public void before() {
|
||||||
|
myHttpClient = mock(HttpClient.class, new ReturnsDeepStubs());
|
||||||
|
ourCtx.getRestfulClientFactory().setHttpClient(myHttpClient);
|
||||||
|
|
||||||
|
myHttpResponse = mock(HttpResponse.class, new ReturnsDeepStubs());
|
||||||
|
}
|
||||||
|
|
||||||
|
private String crerateMsg() {
|
||||||
|
//@formatter:off
|
||||||
|
String msg = "<Patient xmlns=\"http://hl7.org/fhir\">"
|
||||||
|
+ "<text><status value=\"generated\" /><div xmlns=\"http://www.w3.org/1999/xhtml\">John Cardinal: 444333333 </div></text>"
|
||||||
|
+ "<identifier><label value=\"SSN\" /><system value=\"http://orionhealth.com/mrn\" /><value value=\"PRP1660\" /></identifier>"
|
||||||
|
+ "<name><use value=\"official\" /><family value=\"Cardinal\" /><given value=\"John\" /></name>"
|
||||||
|
+ "<name><family value=\"Kramer\" /><given value=\"Doe\" /></name>"
|
||||||
|
+ "<telecom><system value=\"phone\" /><value value=\"555-555-2004\" /><use value=\"work\" /></telecom>"
|
||||||
|
+ "<gender><coding><system value=\"http://hl7.org/fhir/v3/AdministrativeGender\" /><code value=\"M\" /></coding></gender>"
|
||||||
|
+ "<address><use value=\"home\" /><line value=\"2222 Home Street\" /></address><active value=\"true\" />"
|
||||||
|
+ "</Patient>";
|
||||||
|
//@formatter:on
|
||||||
|
return msg;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void testRequest() throws Exception {
|
||||||
|
String msg = crerateMsg();
|
||||||
|
|
||||||
|
ArgumentCaptor<HttpUriRequest> capt = ArgumentCaptor.forClass(HttpUriRequest.class);
|
||||||
|
when(myHttpClient.execute(capt.capture())).thenReturn(myHttpResponse);
|
||||||
|
when(myHttpResponse.getStatusLine()).thenReturn(new BasicStatusLine(new ProtocolVersion("HTTP", 1, 1), 200, "OK"));
|
||||||
|
Header[] headers = new Header[] {};
|
||||||
|
|
||||||
|
when(myHttpResponse.getAllHeaders()).thenReturn(headers);
|
||||||
|
when(myHttpResponse.getEntity().getContentType()).thenReturn(new BasicHeader("content-type", Constants.CT_FHIR_XML + "; charset=UTF-8"));
|
||||||
|
when(myHttpResponse.getEntity().getContent()).thenReturn(new ReaderInputStream(new StringReader(msg), Charset.forName("UTF-8")));
|
||||||
|
|
||||||
|
ITestClient client = ourCtx.newRestfulClient(ITestClient.class, "http://foo");
|
||||||
|
client.registerInterceptor(new BearerTokenAuthInterceptor("mytoken"));
|
||||||
|
client.getPatientById(new IdDt("111"));
|
||||||
|
|
||||||
|
HttpUriRequest req = capt.getValue();
|
||||||
|
assertEquals("Bearer mytoken", req.getFirstHeader("Authorization").getValue());
|
||||||
|
}
|
||||||
|
|
||||||
|
@BeforeClass
|
||||||
|
public static void beforeClass() {
|
||||||
|
ourCtx = new FhirContext();
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -1,15 +1,17 @@
|
||||||
package ca.uhn.fhir.rest.client;
|
package ca.uhn.fhir.rest.client;
|
||||||
|
|
||||||
import static org.junit.Assert.*;
|
import static org.junit.Assert.assertFalse;
|
||||||
import static org.mockito.Matchers.*;
|
import static org.mockito.Matchers.argThat;
|
||||||
import static org.mockito.Mockito.*;
|
import static org.mockito.Mockito.mock;
|
||||||
|
import static org.mockito.Mockito.verify;
|
||||||
import java.util.ResourceBundle;
|
import static org.mockito.Mockito.when;
|
||||||
|
|
||||||
import org.eclipse.jetty.server.Server;
|
import org.eclipse.jetty.server.Server;
|
||||||
import org.eclipse.jetty.servlet.ServletHandler;
|
import org.eclipse.jetty.servlet.ServletHandler;
|
||||||
import org.eclipse.jetty.servlet.ServletHolder;
|
import org.eclipse.jetty.servlet.ServletHolder;
|
||||||
|
import org.junit.After;
|
||||||
import org.junit.AfterClass;
|
import org.junit.AfterClass;
|
||||||
|
import org.junit.Before;
|
||||||
import org.junit.BeforeClass;
|
import org.junit.BeforeClass;
|
||||||
import org.junit.Test;
|
import org.junit.Test;
|
||||||
import org.mockito.ArgumentMatcher;
|
import org.mockito.ArgumentMatcher;
|
||||||
|
@ -23,9 +25,9 @@ import ca.uhn.fhir.rest.annotation.IdParam;
|
||||||
import ca.uhn.fhir.rest.annotation.Read;
|
import ca.uhn.fhir.rest.annotation.Read;
|
||||||
import ca.uhn.fhir.rest.client.interceptor.LoggingInterceptor;
|
import ca.uhn.fhir.rest.client.interceptor.LoggingInterceptor;
|
||||||
import ca.uhn.fhir.rest.server.IResourceProvider;
|
import ca.uhn.fhir.rest.server.IResourceProvider;
|
||||||
import ca.uhn.fhir.rest.server.ResourceBinding;
|
|
||||||
import ca.uhn.fhir.rest.server.RestfulServer;
|
import ca.uhn.fhir.rest.server.RestfulServer;
|
||||||
import ca.uhn.fhir.util.PortUtil;
|
import ca.uhn.fhir.util.PortUtil;
|
||||||
|
import ch.qos.logback.classic.Logger;
|
||||||
import ch.qos.logback.classic.spi.ILoggingEvent;
|
import ch.qos.logback.classic.spi.ILoggingEvent;
|
||||||
import ch.qos.logback.classic.spi.LoggingEvent;
|
import ch.qos.logback.classic.spi.LoggingEvent;
|
||||||
import ch.qos.logback.core.Appender;
|
import ch.qos.logback.core.Appender;
|
||||||
|
@ -33,44 +35,45 @@ import ch.qos.logback.core.Appender;
|
||||||
/**
|
/**
|
||||||
* Created by dsotnikov on 2/25/2014.
|
* Created by dsotnikov on 2/25/2014.
|
||||||
*/
|
*/
|
||||||
public class InterceptorTest {
|
public class LoggingInterceptorTest {
|
||||||
|
|
||||||
private static int ourPort;
|
private static int ourPort;
|
||||||
private static Server ourServer;
|
private static Server ourServer;
|
||||||
private static FhirContext ourCtx;
|
private static FhirContext ourCtx;
|
||||||
|
|
||||||
|
private Appender<ILoggingEvent> myMockAppender;
|
||||||
|
private Logger myLoggerRoot;
|
||||||
|
|
||||||
|
@SuppressWarnings("unchecked")
|
||||||
|
@Before
|
||||||
|
public void before() {
|
||||||
|
/*
|
||||||
|
* This is a bit funky, but it's useful for verifying that the headers actually get logged
|
||||||
|
*/
|
||||||
|
myLoggerRoot = (ch.qos.logback.classic.Logger) LoggerFactory.getLogger(ch.qos.logback.classic.Logger.ROOT_LOGGER_NAME);
|
||||||
|
myMockAppender = mock(Appender.class);
|
||||||
|
when(myMockAppender.getName()).thenReturn("MOCK");
|
||||||
|
myLoggerRoot.addAppender(myMockAppender);
|
||||||
|
}
|
||||||
|
|
||||||
|
@After
|
||||||
|
public void after() {
|
||||||
|
myLoggerRoot.detachAppender(myMockAppender);
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void testLogger() throws Exception {
|
public void testLogger() throws Exception {
|
||||||
/*
|
|
||||||
* This is a bit funky, but we're verifying that the headers actually get logged
|
|
||||||
*/
|
|
||||||
ch.qos.logback.classic.Logger root = (ch.qos.logback.classic.Logger) LoggerFactory.getLogger(ch.qos.logback.classic.Logger.ROOT_LOGGER_NAME);
|
|
||||||
@SuppressWarnings("unchecked")
|
|
||||||
Appender<ILoggingEvent> mockAppender = mock(Appender.class);
|
|
||||||
when(mockAppender.getName()).thenReturn("MOCK");
|
|
||||||
root.addAppender(mockAppender);
|
|
||||||
try {
|
|
||||||
|
|
||||||
IGenericClient client = ourCtx.newRestfulGenericClient("http://localhost:" + ourPort);
|
IGenericClient client = ourCtx.newRestfulGenericClient("http://localhost:" + ourPort);
|
||||||
client.registerInterceptor(new LoggingInterceptor(true));
|
client.registerInterceptor(new LoggingInterceptor(true));
|
||||||
Patient patient = client.read(Patient.class, "1");
|
Patient patient = client.read(Patient.class, "1");
|
||||||
assertFalse(patient.getIdentifierFirstRep().isEmpty());
|
assertFalse(patient.getIdentifierFirstRep().isEmpty());
|
||||||
|
|
||||||
// int times = 1;
|
verify(myMockAppender).doAppend(argThat(new ArgumentMatcher<ILoggingEvent>() {
|
||||||
// if (LoggerFactory.getLogger(ResourceBinding.class).isDebugEnabled()) {
|
|
||||||
// times = 3;
|
|
||||||
// }
|
|
||||||
|
|
||||||
verify(mockAppender).doAppend(argThat(new ArgumentMatcher<ILoggingEvent>() {
|
|
||||||
@Override
|
@Override
|
||||||
public boolean matches(final Object argument) {
|
public boolean matches(final Object argument) {
|
||||||
return ((LoggingEvent) argument).getFormattedMessage().contains("Content-Type: application/xml+fhir; charset=UTF-8");
|
return ((LoggingEvent) argument).getFormattedMessage().contains("Content-Type: application/xml+fhir; charset=UTF-8");
|
||||||
}
|
}
|
||||||
}));
|
}));
|
||||||
|
|
||||||
} finally {
|
|
||||||
root.detachAppender(mockAppender);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@AfterClass
|
@AfterClass
|
Binary file not shown.
Binary file not shown.
Binary file not shown.
|
@ -47,8 +47,6 @@ import com.nimbusds.jwt.SignedJWT;
|
||||||
|
|
||||||
public class OpenIdConnectBearerTokenServerInterceptor extends InterceptorAdapter {
|
public class OpenIdConnectBearerTokenServerInterceptor extends InterceptorAdapter {
|
||||||
|
|
||||||
private static final String BEARER_PREFIX = "Bearer ";
|
|
||||||
|
|
||||||
private static final org.slf4j.Logger ourLog = org.slf4j.LoggerFactory.getLogger(OpenIdConnectBearerTokenServerInterceptor.class);
|
private static final org.slf4j.Logger ourLog = org.slf4j.LoggerFactory.getLogger(OpenIdConnectBearerTokenServerInterceptor.class);
|
||||||
|
|
||||||
@Autowired
|
@Autowired
|
||||||
|
@ -68,8 +66,6 @@ public class OpenIdConnectBearerTokenServerInterceptor extends InterceptorAdapte
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean incomingRequestPostProcessed(RequestDetails theRequestDetails, HttpServletRequest theRequest, HttpServletResponse theResponse) throws AuthenticationException {
|
public boolean incomingRequestPostProcessed(RequestDetails theRequestDetails, HttpServletRequest theRequest, HttpServletResponse theResponse) throws AuthenticationException {
|
||||||
if (theRequestDetails.getOtherOperationType() == OtherOperationTypeEnum.METADATA) {
|
if (theRequestDetails.getOtherOperationType() == OtherOperationTypeEnum.METADATA) {
|
||||||
|
@ -89,11 +85,11 @@ public class OpenIdConnectBearerTokenServerInterceptor extends InterceptorAdapte
|
||||||
if (token == null) {
|
if (token == null) {
|
||||||
throw new AuthenticationException("Not authorized (no authorization header found in request)");
|
throw new AuthenticationException("Not authorized (no authorization header found in request)");
|
||||||
}
|
}
|
||||||
if (!token.startsWith(BEARER_PREFIX)) {
|
if (!token.startsWith(Constants.HEADER_AUTHORIZATION_VALPREFIX_BEARER)) {
|
||||||
throw new AuthenticationException("Not authorized (authorization header does not contain a bearer token)");
|
throw new AuthenticationException("Not authorized (authorization header does not contain a bearer token)");
|
||||||
}
|
}
|
||||||
|
|
||||||
token = token.substring(BEARER_PREFIX.length());
|
token = token.substring(Constants.HEADER_AUTHORIZATION_VALPREFIX_BEARER.length());
|
||||||
|
|
||||||
SignedJWT idToken;
|
SignedJWT idToken;
|
||||||
try {
|
try {
|
||||||
|
|
Loading…
Reference in New Issue