JPA module now handles search params with | in them - More work on #52

This commit is contained in:
James Agnew 2014-11-18 13:10:13 -05:00
parent 93c34fdbbe
commit 14a8f4f4cf
9 changed files with 198 additions and 38 deletions

View File

@ -511,6 +511,10 @@ public class GenericClient extends BaseClient implements IGenericClient {
return resp; return resp;
} }
protected EncodingEnum getParamEncoding() {
return myParamEncoding;
}
protected IResource parseResourceBody(String theResourceBody) { protected IResource parseResourceBody(String theResourceBody) {
EncodingEnum encoding = null; EncodingEnum encoding = null;
for (int i = 0; i < theResourceBody.length() && encoding == null; i++) { for (int i = 0; i < theResourceBody.length() && encoding == null; i++) {
@ -571,6 +575,11 @@ public class GenericClient extends BaseClient implements IGenericClient {
} }
myId = getPreferredId(myResource, myId); myId = getPreferredId(myResource, myId);
// If an explicit encoding is chosen, we will re-serialize to ensure the right encoding
if (getParamEncoding() != null) {
myResourceBody = null;
}
BaseHttpClientInvocation invocation = MethodUtil.createCreateInvocation(myResource, myResourceBody, myId, myContext); BaseHttpClientInvocation invocation = MethodUtil.createCreateInvocation(myResource, myResourceBody, myId, myContext);
RuntimeResourceDefinition def = myContext.getResourceDefinition(myResource); RuntimeResourceDefinition def = myContext.getResourceDefinition(myResource);
@ -1102,6 +1111,11 @@ public class GenericClient extends BaseClient implements IGenericClient {
throw new InvalidRequestException("No ID supplied for resource to update, can not invoke server"); throw new InvalidRequestException("No ID supplied for resource to update, can not invoke server");
} }
// If an explicit encoding is chosen, we will re-serialize to ensure the right encoding
if (getParamEncoding() != null) {
myResourceBody = null;
}
BaseHttpClientInvocation invocation = MethodUtil.createUpdateInvocation(myResource, myResourceBody, myId, myContext); BaseHttpClientInvocation invocation = MethodUtil.createUpdateInvocation(myResource, myResourceBody, myId, myContext);
RuntimeResourceDefinition def = myContext.getResourceDefinition(myResource); RuntimeResourceDefinition def = myContext.getResourceDefinition(myResource);

View File

@ -44,6 +44,7 @@ import ca.uhn.fhir.model.dstu.resource.Binary;
import ca.uhn.fhir.parser.DataFormatException; import ca.uhn.fhir.parser.DataFormatException;
import ca.uhn.fhir.parser.IParser; import ca.uhn.fhir.parser.IParser;
import ca.uhn.fhir.rest.client.BaseHttpClientInvocation; import ca.uhn.fhir.rest.client.BaseHttpClientInvocation;
import ca.uhn.fhir.rest.server.Constants;
import ca.uhn.fhir.rest.server.EncodingEnum; import ca.uhn.fhir.rest.server.EncodingEnum;
import ca.uhn.fhir.rest.server.RestfulServer; import ca.uhn.fhir.rest.server.RestfulServer;
import ca.uhn.fhir.rest.server.exceptions.InternalErrorException; import ca.uhn.fhir.rest.server.exceptions.InternalErrorException;
@ -165,6 +166,10 @@ abstract class BaseHttpClientInvocationWithContents extends BaseHttpClientInvoca
EncodingEnum encoding = null; EncodingEnum encoding = null;
encoding = theEncoding; encoding = theEncoding;
if (myContents != null) {
encoding = MethodUtil.detectEncoding(myContents);
}
if (encoding == EncodingEnum.JSON) { if (encoding == EncodingEnum.JSON) {
parser = myContext.newJsonParser(); parser = myContext.newJsonParser();
} else { } else {
@ -174,6 +179,7 @@ abstract class BaseHttpClientInvocationWithContents extends BaseHttpClientInvoca
AbstractHttpEntity entity; AbstractHttpEntity entity;
if (myParams != null) { if (myParams != null) {
contentType= null;
List<NameValuePair> parameters = new ArrayList<NameValuePair>(); List<NameValuePair> parameters = new ArrayList<NameValuePair>();
for (Entry<String, List<String>> nextParam : myParams.entrySet()) { for (Entry<String, List<String>> nextParam : myParams.entrySet()) {
List<String> value = nextParam.getValue(); List<String> value = nextParam.getValue();
@ -215,7 +221,9 @@ abstract class BaseHttpClientInvocationWithContents extends BaseHttpClientInvoca
HttpRequestBase retVal = createRequest(url, entity); HttpRequestBase retVal = createRequest(url, entity);
super.addHeadersToRequest(retVal); super.addHeadersToRequest(retVal);
// retVal.addHeader(Constants.HEADER_CONTENT_TYPE, con); if (contentType != null) {
retVal.addHeader(Constants.HEADER_CONTENT_TYPE, contentType);
}
return retVal; return retVal;
} }

View File

@ -115,7 +115,7 @@ public class MethodUtil {
} }
addTagsToPostOrPut(theResource, retVal); addTagsToPostOrPut(theResource, retVal);
addContentTypeHeaderBasedOnDetectedType(retVal, theResourceBody); // addContentTypeHeaderBasedOnDetectedType(retVal, theResourceBody);
return retVal; return retVal;
} }
@ -261,22 +261,21 @@ public class MethodUtil {
} }
addTagsToPostOrPut(theResource, retVal); addTagsToPostOrPut(theResource, retVal);
addContentTypeHeaderBasedOnDetectedType(retVal, theResourceBody); // addContentTypeHeaderBasedOnDetectedType(retVal, theResourceBody);
return retVal; return retVal;
} }
private static void addContentTypeHeaderBasedOnDetectedType(BaseHttpClientInvocationWithContents theHttpMethod, String theBody) { public static EncodingEnum detectEncoding(String theBody) {
for (int i = 0; i < theBody.length(); i++) { for (int i = 0; i < theBody.length(); i++) {
switch (theBody.charAt(i)) { switch (theBody.charAt(i)) {
case '<': case '<':
theHttpMethod.addHeader(Constants.HEADER_CONTENT_TYPE, EncodingEnum.XML.getResourceContentType()); return EncodingEnum.XML;
return;
case '{': case '{':
theHttpMethod.addHeader(Constants.HEADER_CONTENT_TYPE, EncodingEnum.JSON.getResourceContentType()); return EncodingEnum.JSON;
return;
} }
} }
return EncodingEnum.XML;
} }
public static HttpGetClientInvocation createConformanceInvocation() { public static HttpGetClientInvocation createConformanceInvocation() {

View File

@ -312,17 +312,28 @@ public abstract class BaseFhirDao implements IDao {
continue; continue;
} }
String nextPath = nextSpDef.getPath(); String nextPathsUnsplit = nextSpDef.getPath();
if (isBlank(nextPath)) { if (isBlank(nextPathsUnsplit)) {
continue; continue;
} }
boolean multiType = false; boolean multiType = false;
if (nextPath.endsWith("[x]")) { if (nextPathsUnsplit.endsWith("[x]")) {
multiType = true; multiType = true;
} }
List<Object> values = t.getValues(theResource, nextPath); List<Object> values = new ArrayList<Object>();
String[] nextPathsSplit = nextPathsUnsplit.split("\\|");
for (String nextPath : nextPathsSplit) {
String nextPathTrimmed = nextPath.trim();
try {
values.addAll(t.getValues(theResource, nextPathTrimmed));
} catch (Exception e) {
ourLog.warn("Failed to index values from path[{}] in resource type[{}]: ", nextPathTrimmed, def.getName(), e.toString());
}
}
for (Object nextObject : values) { for (Object nextObject : values) {
if (nextObject == null) { if (nextObject == null) {
continue; continue;
@ -341,7 +352,7 @@ public abstract class BaseFhirDao implements IDao {
String typeString = nextValue.getReference().getResourceType(); String typeString = nextValue.getReference().getResourceType();
if (isBlank(typeString)) { if (isBlank(typeString)) {
throw new InvalidRequestException("Invalid resource reference found at path[" + nextPath + "] - Does not contain resource type - " + nextValue.getReference().getValue()); throw new InvalidRequestException("Invalid resource reference found at path[" + nextPathsUnsplit + "] - Does not contain resource type - " + nextValue.getReference().getValue());
} }
Class<? extends IResource> type = getContext().getResourceDefinition(typeString).getImplementingClass(); Class<? extends IResource> type = getContext().getResourceDefinition(typeString).getImplementingClass();
String id = nextValue.getReference().getIdPart(); String id = nextValue.getReference().getIdPart();
@ -358,14 +369,14 @@ public abstract class BaseFhirDao implements IDao {
valueOf = translateForcedIdToPid(nextValue.getReference()); valueOf = translateForcedIdToPid(nextValue.getReference());
} catch (Exception e) { } catch (Exception e) {
String resName = getContext().getResourceDefinition(type).getName(); String resName = getContext().getResourceDefinition(type).getName();
throw new InvalidRequestException("Resource " + resName + "/" + id + " not found, specified in path: " + nextPath + " (this is an invalid ID, must be numeric on this server)"); throw new InvalidRequestException("Resource " + resName + "/" + id + " not found, specified in path: " + nextPathsUnsplit + " (this is an invalid ID, must be numeric on this server)");
} }
ResourceTable target = myEntityManager.find(ResourceTable.class, valueOf); ResourceTable target = myEntityManager.find(ResourceTable.class, valueOf);
if (target == null) { if (target == null) {
String resName = getContext().getResourceDefinition(type).getName(); String resName = getContext().getResourceDefinition(type).getName();
throw new InvalidRequestException("Resource " + resName + "/" + id + " not found, specified in path: " + nextPath); throw new InvalidRequestException("Resource " + resName + "/" + id + " not found, specified in path: " + nextPathsUnsplit);
} }
nextEntity = new ResourceLink(nextPath, theEntity, target); nextEntity = new ResourceLink(nextPathsUnsplit, theEntity, target);
} else { } else {
if (!multiType) { if (!multiType) {
throw new ConfigurationException("Search param " + nextSpDef.getName() + " is of unexpected datatype: " + nextObject.getClass()); throw new ConfigurationException("Search param " + nextSpDef.getName() + " is of unexpected datatype: " + nextObject.getClass());

View File

@ -138,7 +138,10 @@
<packageBase>ca.uhn.test.jpasrv</packageBase> <packageBase>ca.uhn.test.jpasrv</packageBase>
<baseResourceNames> <baseResourceNames>
<baseResourceName>device</baseResourceName> <baseResourceName>device</baseResourceName>
<baseResourceName>documentmanifest</baseResourceName>
<baseResourceName>documentreference</baseResourceName>
<baseResourceName>encounter</baseResourceName> <baseResourceName>encounter</baseResourceName>
<baseResourceName>diagnosticorder</baseResourceName>
<baseResourceName>diagnosticreport</baseResourceName> <baseResourceName>diagnosticreport</baseResourceName>
<baseResourceName>imagingstudy</baseResourceName> <baseResourceName>imagingstudy</baseResourceName>
<baseResourceName>location</baseResourceName> <baseResourceName>location</baseResourceName>

View File

@ -46,6 +46,17 @@
<property name="resourceType" value="ca.uhn.fhir.model.dstu.resource.Encounter"/> <property name="resourceType" value="ca.uhn.fhir.model.dstu.resource.Encounter"/>
</bean> </bean>
<bean id="myDiagnosticOrderDao" class="ca.uhn.fhir.jpa.dao.FhirResourceDao">
<property name="resourceType" value="ca.uhn.fhir.model.dstu.resource.DiagnosticOrder"/>
</bean>
<bean id="myDocumentManifestDao" class="ca.uhn.fhir.jpa.dao.FhirResourceDao">
<property name="resourceType" value="ca.uhn.fhir.model.dstu.resource.DocumentManifest"/>
</bean>
<bean id="myDocumentReferenceDao" class="ca.uhn.fhir.jpa.dao.FhirResourceDao">
<property name="resourceType" value="ca.uhn.fhir.model.dstu.resource.DocumentReference"/>
</bean>
<bean id="myPersistenceDataSource" class="org.springframework.jdbc.datasource.DriverManagerDataSource" lazy-init="true"> <bean id="myPersistenceDataSource" class="org.springframework.jdbc.datasource.DriverManagerDataSource" lazy-init="true">
<property name="url" value="jdbc:derby:memory:myUnitTestDB;create=true" /> <property name="url" value="jdbc:derby:memory:myUnitTestDB;create=true" />
<!-- <property name="url" value="jdbc:derby:directory:myUnitTestDB;create=true" /> --> <!-- <property name="url" value="jdbc:derby:directory:myUnitTestDB;create=true" /> -->

View File

@ -1,9 +1,11 @@
package ca.uhn.fhir.jpa.test; package ca.uhn.fhir.jpa.test;
import static org.hamcrest.Matchers.*; import static org.hamcrest.Matchers.containsString;
import static org.junit.Assert.*; import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertThat;
import static org.junit.Assert.fail;
import java.io.File;
import java.util.Date; import java.util.Date;
import org.apache.commons.io.IOUtils; import org.apache.commons.io.IOUtils;
@ -24,6 +26,9 @@ import ca.uhn.fhir.model.api.Bundle;
import ca.uhn.fhir.model.api.IResource; import ca.uhn.fhir.model.api.IResource;
import ca.uhn.fhir.model.dstu.composite.PeriodDt; import ca.uhn.fhir.model.dstu.composite.PeriodDt;
import ca.uhn.fhir.model.dstu.composite.ResourceReferenceDt; import ca.uhn.fhir.model.dstu.composite.ResourceReferenceDt;
import ca.uhn.fhir.model.dstu.resource.DiagnosticOrder;
import ca.uhn.fhir.model.dstu.resource.DocumentManifest;
import ca.uhn.fhir.model.dstu.resource.DocumentReference;
import ca.uhn.fhir.model.dstu.resource.Encounter; import ca.uhn.fhir.model.dstu.resource.Encounter;
import ca.uhn.fhir.model.dstu.resource.ImagingStudy; import ca.uhn.fhir.model.dstu.resource.ImagingStudy;
import ca.uhn.fhir.model.dstu.resource.Location; import ca.uhn.fhir.model.dstu.resource.Location;
@ -44,6 +49,9 @@ import ca.uhn.fhir.rest.gclient.TokenClientParam;
import ca.uhn.fhir.rest.server.RestfulServer; import ca.uhn.fhir.rest.server.RestfulServer;
import ca.uhn.fhir.rest.server.exceptions.InvalidRequestException; import ca.uhn.fhir.rest.server.exceptions.InvalidRequestException;
import ca.uhn.fhir.rest.server.exceptions.UnprocessableEntityException; import ca.uhn.fhir.rest.server.exceptions.UnprocessableEntityException;
import ca.uhn.test.jpasrv.DiagnosticOrderResourceProvider;
import ca.uhn.test.jpasrv.DocumentManifestResourceProvider;
import ca.uhn.test.jpasrv.DocumentReferenceResourceProvider;
import ca.uhn.test.jpasrv.EncounterResourceProvider; import ca.uhn.test.jpasrv.EncounterResourceProvider;
import ca.uhn.test.jpasrv.ImagingStudyResourceProvider; import ca.uhn.test.jpasrv.ImagingStudyResourceProvider;
import ca.uhn.test.jpasrv.LocationResourceProvider; import ca.uhn.test.jpasrv.LocationResourceProvider;
@ -83,6 +91,28 @@ public class CompleteResourceProviderTest {
} }
/**
* See issue #52
*/
@Test
public void testDiagnosticOrderResources() throws Exception {
IGenericClient client = ourClient;
int initialSize = client.search().forResource(DiagnosticOrder.class).execute().size();
DiagnosticOrder res = new DiagnosticOrder();
res.addIdentifier("urn:foo", "123");
client.create().resource(res).execute();
int newSize = client.search().forResource(DiagnosticOrder.class).execute().size();
assertEquals(1, newSize - initialSize);
}
private void delete(String theResourceType, String theParamName, String theParamValue) { private void delete(String theResourceType, String theParamName, String theParamValue) {
Bundle resources = ourClient.search().forResource(theResourceType).where(new StringClientParam(theParamName).matches().value(theParamValue)).execute(); Bundle resources = ourClient.search().forResource(theResourceType).where(new StringClientParam(theParamName).matches().value(theParamValue)).execute();
for (IResource next : resources.toListOfResources()) { for (IResource next : resources.toListOfResources()) {
@ -392,7 +422,19 @@ public class CompleteResourceProviderTest {
ImagingStudyResourceProvider imagingStudyRp = new ImagingStudyResourceProvider(); ImagingStudyResourceProvider imagingStudyRp = new ImagingStudyResourceProvider();
imagingStudyRp.setDao(imagingStudyDao); imagingStudyRp.setDao(imagingStudyDao);
restServer.setResourceProviders(encounterRp, locationRp, patientRp, questionnaireRp, observationRp, organizationRp, imagingStudyRp); IFhirResourceDao<DiagnosticOrder> diagnosticOrderDao =ourAppCtx.getBean("myDiagnosticOrderDao", IFhirResourceDao.class);
DiagnosticOrderResourceProvider diagnosticOrderRp = new DiagnosticOrderResourceProvider();
diagnosticOrderRp.setDao(diagnosticOrderDao);
IFhirResourceDao<DocumentManifest> documentManifestDao =ourAppCtx.getBean("myDocumentManifestDao", IFhirResourceDao.class);
DocumentManifestResourceProvider documentManifestRp = new DocumentManifestResourceProvider();
documentManifestRp.setDao(documentManifestDao);
IFhirResourceDao<DocumentReference> documentReferenceDao =ourAppCtx.getBean("myDocumentReferenceDao", IFhirResourceDao.class);
DocumentReferenceResourceProvider documentReferenceRp = new DocumentReferenceResourceProvider();
documentReferenceRp.setDao(documentReferenceDao);
restServer.setResourceProviders(diagnosticOrderRp, documentManifestRp, documentReferenceRp, encounterRp, locationRp, patientRp, questionnaireRp, observationRp, organizationRp, imagingStudyRp);
restServer.getFhirContext().setNarrativeGenerator(new DefaultThymeleafNarrativeGenerator()); restServer.getFhirContext().setNarrativeGenerator(new DefaultThymeleafNarrativeGenerator());
IFhirSystemDao systemDao = (IFhirSystemDao) ourAppCtx.getBean("mySystemDao", IFhirSystemDao.class); IFhirSystemDao systemDao = (IFhirSystemDao) ourAppCtx.getBean("mySystemDao", IFhirSystemDao.class);

View File

@ -4,6 +4,7 @@ import static org.hamcrest.Matchers.*;
import static org.junit.Assert.*; import static org.junit.Assert.*;
import static org.mockito.Mockito.*; import static org.mockito.Mockito.*;
import java.io.IOException;
import java.io.StringReader; import java.io.StringReader;
import java.net.URLEncoder; import java.net.URLEncoder;
import java.nio.charset.Charset; import java.nio.charset.Charset;
@ -178,11 +179,16 @@ public class GenericClientTest {
assertEquals("44", outcome.getId().getIdPart()); assertEquals("44", outcome.getId().getIdPart());
assertEquals("22", outcome.getId().getVersionIdPart()); assertEquals("22", outcome.getId().getVersionIdPart());
int count = 0;
assertEquals("http://example.com/fhir/Patient", capt.getValue().getURI().toString()); assertEquals("http://example.com/fhir/Patient", capt.getValue().getURI().toString());
assertEquals("POST", capt.getValue().getMethod()); assertEquals("POST", capt.getValue().getMethod());
Header catH = capt.getValue().getFirstHeader("Category"); Header catH = capt.getValue().getFirstHeader("Category");
assertNotNull(Arrays.asList(capt.getValue().getAllHeaders()).toString(), catH); assertNotNull(Arrays.asList(capt.getValue().getAllHeaders()).toString(), catH);
assertEquals("urn:happytag; label=\"This is a happy resource\"; scheme=\"http://hl7.org/fhir/tag\"", catH.getValue()); assertEquals("urn:happytag; label=\"This is a happy resource\"; scheme=\"http://hl7.org/fhir/tag\"", catH.getValue());
assertEquals(1, capt.getAllValues().get(count).getHeaders(Constants.HEADER_CONTENT_TYPE).length);
assertEquals(EncodingEnum.XML.getResourceContentType(), capt.getAllValues().get(count).getFirstHeader(Constants.HEADER_CONTENT_TYPE).getValue());
count++;
/* /*
* Try fluent options * Try fluent options
@ -190,16 +196,20 @@ public class GenericClientTest {
when(myHttpResponse.getEntity().getContent()).thenReturn(new ReaderInputStream(new StringReader(""), Charset.forName("UTF-8"))); when(myHttpResponse.getEntity().getContent()).thenReturn(new ReaderInputStream(new StringReader(""), Charset.forName("UTF-8")));
client.create().resource(p1).withId("123").execute(); client.create().resource(p1).withId("123").execute();
assertEquals("http://example.com/fhir/Patient/123", capt.getAllValues().get(1).getURI().toString()); assertEquals("http://example.com/fhir/Patient/123", capt.getAllValues().get(1).getURI().toString());
assertEquals(1, capt.getAllValues().get(count).getHeaders(Constants.HEADER_CONTENT_TYPE).length);
assertEquals(EncodingEnum.XML.getResourceContentType(), capt.getAllValues().get(count).getFirstHeader(Constants.HEADER_CONTENT_TYPE).getValue());
count++;
String resourceText = "<Patient xmlns=\"http://hl7.org/fhir\"> </Patient>"; String resourceText = "<Patient xmlns=\"http://hl7.org/fhir\"> </Patient>";
when(myHttpResponse.getEntity().getContent()).thenReturn(new ReaderInputStream(new StringReader(""), Charset.forName("UTF-8"))); when(myHttpResponse.getEntity().getContent()).thenReturn(new ReaderInputStream(new StringReader(""), Charset.forName("UTF-8")));
client.create().resource(resourceText).withId("123").execute(); client.create().resource(resourceText).withId("123").execute();
assertEquals("http://example.com/fhir/Patient/123", capt.getAllValues().get(2).getURI().toString()); assertEquals("http://example.com/fhir/Patient/123", capt.getAllValues().get(2).getURI().toString());
assertEquals(resourceText, IOUtils.toString(((HttpPost) capt.getAllValues().get(2)).getEntity().getContent())); assertEquals(resourceText, IOUtils.toString(((HttpPost) capt.getAllValues().get(2)).getEntity().getContent()));
assertEquals(1, capt.getAllValues().get(count).getHeaders(Constants.HEADER_CONTENT_TYPE).length);
assertEquals(EncodingEnum.XML.getResourceContentType(), capt.getAllValues().get(count).getFirstHeader(Constants.HEADER_CONTENT_TYPE).getValue());
count++;
} }
@Test @Test
public void testCreateWithStringAutoDetectsEncoding() throws Exception { public void testCreateWithStringAutoDetectsEncoding() throws Exception {
@ -218,10 +228,38 @@ public class GenericClientTest {
int count = 0; int count = 0;
client.create().resource(myCtx.newXmlParser().encodeResourceToString(p1)).execute(); client.create().resource(myCtx.newXmlParser().encodeResourceToString(p1)).execute();
assertEquals(EncodingEnum.XML.getResourceContentType(), capt.getAllValues().get(count++).getFirstHeader(Constants.HEADER_CONTENT_TYPE).getValue()); assertEquals(1, capt.getAllValues().get(count).getHeaders(Constants.HEADER_CONTENT_TYPE).length);
assertEquals(EncodingEnum.XML.getResourceContentType(), capt.getAllValues().get(count).getFirstHeader(Constants.HEADER_CONTENT_TYPE).getValue());
assertThat(extractBody(capt, count), containsString("value=\"John\""));
count++;
client.create().resource(myCtx.newJsonParser().encodeResourceToString(p1)).execute(); client.create().resource(myCtx.newJsonParser().encodeResourceToString(p1)).execute();
assertEquals(EncodingEnum.JSON.getResourceContentType(), capt.getAllValues().get(count++).getFirstHeader(Constants.HEADER_CONTENT_TYPE).getValue()); assertEquals(1, capt.getAllValues().get(count).getHeaders(Constants.HEADER_CONTENT_TYPE).length);
assertEquals(EncodingEnum.JSON.getResourceContentType(), capt.getAllValues().get(count).getFirstHeader(Constants.HEADER_CONTENT_TYPE).getValue());
assertThat(extractBody(capt, count), containsString("[\"John\"]"));
count++;
/*
* e.g. Now try with reversed encoding (provide a string that's in JSON and ask the client to use XML)
*/
client.create().resource(myCtx.newXmlParser().encodeResourceToString(p1)).encodedJson().execute();
assertEquals(1, capt.getAllValues().get(count).getHeaders(Constants.HEADER_CONTENT_TYPE).length);
assertEquals(EncodingEnum.JSON.getResourceContentType(), capt.getAllValues().get(count).getFirstHeader(Constants.HEADER_CONTENT_TYPE).getValue());
assertThat(extractBody(capt, count), containsString("[\"John\"]"));
count++;
client.create().resource(myCtx.newJsonParser().encodeResourceToString(p1)).encodedXml().execute();
assertEquals(1, capt.getAllValues().get(count).getHeaders(Constants.HEADER_CONTENT_TYPE).length);
assertEquals(EncodingEnum.XML.getResourceContentType(), capt.getAllValues().get(count).getFirstHeader(Constants.HEADER_CONTENT_TYPE).getValue());
assertThat(extractBody(capt, count), containsString("value=\"John\""));
count++;
}
private String extractBody(ArgumentCaptor<HttpUriRequest> capt, int count) throws IOException {
String body = IOUtils.toString(((HttpEntityEnclosingRequestBase) capt.getAllValues().get(count)).getEntity().getContent());
return body;
} }
@Test @Test
@ -242,12 +280,33 @@ public class GenericClientTest {
int count = 0; int count = 0;
client.update().resource(myCtx.newXmlParser().encodeResourceToString(p1)).withId("1").execute(); client.update().resource(myCtx.newXmlParser().encodeResourceToString(p1)).withId("1").execute();
assertEquals(EncodingEnum.XML.getResourceContentType(), capt.getAllValues().get(count++).getFirstHeader(Constants.HEADER_CONTENT_TYPE).getValue()); assertEquals(1, capt.getAllValues().get(count).getHeaders(Constants.HEADER_CONTENT_TYPE).length);
assertEquals(EncodingEnum.XML.getResourceContentType(), capt.getAllValues().get(count).getFirstHeader(Constants.HEADER_CONTENT_TYPE).getValue());
assertThat(extractBody(capt, count), containsString("value=\"John\""));
count++;
client.update().resource(myCtx.newJsonParser().encodeResourceToString(p1)).withId("1").execute(); client.update().resource(myCtx.newJsonParser().encodeResourceToString(p1)).withId("1").execute();
assertEquals(EncodingEnum.JSON.getResourceContentType(), capt.getAllValues().get(count++).getFirstHeader(Constants.HEADER_CONTENT_TYPE).getValue()); assertEquals(1, capt.getAllValues().get(count).getHeaders(Constants.HEADER_CONTENT_TYPE).length);
} assertEquals(EncodingEnum.JSON.getResourceContentType(), capt.getAllValues().get(count).getFirstHeader(Constants.HEADER_CONTENT_TYPE).getValue());
assertThat(extractBody(capt, count), containsString("[\"John\"]"));
count++;
/*
* e.g. Now try with reversed encoding (provide a string that's in JSON and ask the client to use XML)
*/
client.update().resource(myCtx.newXmlParser().encodeResourceToString(p1)).withId("1").encodedJson().execute();
assertEquals(1, capt.getAllValues().get(count).getHeaders(Constants.HEADER_CONTENT_TYPE).length);
assertEquals(EncodingEnum.JSON.getResourceContentType(), capt.getAllValues().get(count).getFirstHeader(Constants.HEADER_CONTENT_TYPE).getValue());
assertThat(extractBody(capt, count), containsString("[\"John\"]"));
count++;
client.update().resource(myCtx.newJsonParser().encodeResourceToString(p1)).withId("1").encodedXml().execute();
assertEquals(1, capt.getAllValues().get(count).getHeaders(Constants.HEADER_CONTENT_TYPE).length);
assertEquals(EncodingEnum.XML.getResourceContentType(), capt.getAllValues().get(count).getFirstHeader(Constants.HEADER_CONTENT_TYPE).getValue());
assertThat(extractBody(capt, count), containsString("value=\"John\""));
count++;
}
@Test @Test
public void testCreateWithTagNonFluent() throws Exception { public void testCreateWithTagNonFluent() throws Exception {
@ -555,7 +614,6 @@ public class GenericClientTest {
} }
@Test @Test
public void testSearchWithAbsoluteUrl() throws Exception { public void testSearchWithAbsoluteUrl() throws Exception {
@ -569,7 +627,9 @@ public class GenericClientTest {
IGenericClient client = myCtx.newRestfulGenericClient("http://example.com/fhir"); IGenericClient client = myCtx.newRestfulGenericClient("http://example.com/fhir");
Bundle response = client.search(new UriDt("http://example.com/fhir/Patient?birthdate=%3C%3D2012-01-22&birthdate=%3E2011-01-01&_include=Patient.managingOrganization&_sort%3Aasc=birthdate&_sort%3Adesc=name&_count=123&_format=json")); Bundle response = client
.search(new UriDt(
"http://example.com/fhir/Patient?birthdate=%3C%3D2012-01-22&birthdate=%3E2011-01-01&_include=Patient.managingOrganization&_sort%3Aasc=birthdate&_sort%3Adesc=name&_count=123&_format=json"));
assertEquals( assertEquals(
"http://example.com/fhir/Patient?birthdate=%3C%3D2012-01-22&birthdate=%3E2011-01-01&_include=Patient.managingOrganization&_sort%3Aasc=birthdate&_sort%3Adesc=name&_count=123&_format=json", "http://example.com/fhir/Patient?birthdate=%3C%3D2012-01-22&birthdate=%3E2011-01-01&_include=Patient.managingOrganization&_sort%3Aasc=birthdate&_sort%3Adesc=name&_count=123&_format=json",
@ -578,7 +638,6 @@ public class GenericClientTest {
assertEquals(1, response.size()); assertEquals(1, response.size());
} }
@Test @Test
public void testSearchWithAbsoluteUrlAndType() throws Exception { public void testSearchWithAbsoluteUrlAndType() throws Exception {
@ -592,7 +651,10 @@ public class GenericClientTest {
IGenericClient client = myCtx.newRestfulGenericClient("http://example.com/fhir"); IGenericClient client = myCtx.newRestfulGenericClient("http://example.com/fhir");
Bundle response = client.search(Patient.class, new UriDt("http://example.com/fhir/Patient?birthdate=%3C%3D2012-01-22&birthdate=%3E2011-01-01&_include=Patient.managingOrganization&_sort%3Aasc=birthdate&_sort%3Adesc=name&_count=123&_format=json")); Bundle response = client
.search(Patient.class,
new UriDt(
"http://example.com/fhir/Patient?birthdate=%3C%3D2012-01-22&birthdate=%3E2011-01-01&_include=Patient.managingOrganization&_sort%3Aasc=birthdate&_sort%3Adesc=name&_count=123&_format=json"));
assertEquals( assertEquals(
"http://example.com/fhir/Patient?birthdate=%3C%3D2012-01-22&birthdate=%3E2011-01-01&_include=Patient.managingOrganization&_sort%3Aasc=birthdate&_sort%3Adesc=name&_count=123&_format=json", "http://example.com/fhir/Patient?birthdate=%3C%3D2012-01-22&birthdate=%3E2011-01-01&_include=Patient.managingOrganization&_sort%3Aasc=birthdate&_sort%3Adesc=name&_count=123&_format=json",
@ -1026,7 +1088,12 @@ public class GenericClientTest {
p1.setId("44"); p1.setId("44");
client.update().resource(p1).execute(); client.update().resource(p1).execute();
int count = 0;
assertEquals(1, capt.getAllValues().size()); assertEquals(1, capt.getAllValues().size());
assertEquals(1, capt.getAllValues().get(count).getHeaders(Constants.HEADER_CONTENT_TYPE).length);
assertEquals(EncodingEnum.XML.getResourceContentType(), capt.getAllValues().get(count).getFirstHeader(Constants.HEADER_CONTENT_TYPE).getValue());
count++;
MethodOutcome outcome = client.update().resource(p1).execute(); MethodOutcome outcome = client.update().resource(p1).execute();
assertEquals("44", outcome.getId().getIdPart()); assertEquals("44", outcome.getId().getIdPart());
@ -1039,6 +1106,8 @@ public class GenericClientTest {
Header catH = capt.getValue().getFirstHeader("Category"); Header catH = capt.getValue().getFirstHeader("Category");
assertNotNull(Arrays.asList(capt.getValue().getAllHeaders()).toString(), catH); assertNotNull(Arrays.asList(capt.getValue().getAllHeaders()).toString(), catH);
assertEquals("urn:happytag; label=\"This is a happy resource\"; scheme=\"http://hl7.org/fhir/tag\"", catH.getValue()); assertEquals("urn:happytag; label=\"This is a happy resource\"; scheme=\"http://hl7.org/fhir/tag\"", catH.getValue());
assertEquals(1, capt.getAllValues().get(count).getHeaders(Constants.HEADER_CONTENT_TYPE).length);
assertEquals(EncodingEnum.XML.getResourceContentType(), capt.getAllValues().get(count).getFirstHeader(Constants.HEADER_CONTENT_TYPE).getValue());
/* /*
* Try fluent options * Try fluent options

View File

@ -113,6 +113,9 @@
(although the server does not yet process these params, and it should). Thanks to (although the server does not yet process these params, and it should). Thanks to
GitHub user shvoidlee for reporting and help with analysis! GitHub user shvoidlee for reporting and help with analysis!
</action> </action>
<action type="fix">
Generic/Fluent Client "create" and "update" method requests were not setting a content type header
</action>
</release> </release>
<release version="0.7" date="2014-Oct-23"> <release version="0.7" date="2014-Oct-23">
<action type="add" issue="30"> <action type="add" issue="30">