From a92d80d860e004b992d1e74881ca9cde53728510 Mon Sep 17 00:00:00 2001 From: James Agnew Date: Wed, 17 May 2017 12:40:10 -0400 Subject: [PATCH] Correctly encode extensions on the root of a resource with type reference --- .../java/ca/uhn/fhir/parser/JsonParser.java | 39 +- .../fhir/jpa/dao/BaseHapiFhirResourceDao.java | 6 +- .../dstu3/ResourceProviderDstu3Test.java | 28 +- .../uhn/fhir/parser/JsonParserDstu3Test.java | 556 +- .../uhn/fhir/parser/XmlParserDstu3Test.java | 6316 +++++++++-------- src/changes/changes.xml | 4 + 6 files changed, 3506 insertions(+), 3443 deletions(-) diff --git a/hapi-fhir-base/src/main/java/ca/uhn/fhir/parser/JsonParser.java b/hapi-fhir-base/src/main/java/ca/uhn/fhir/parser/JsonParser.java index 112e6a49ab1..e41dc29ca87 100644 --- a/hapi-fhir-base/src/main/java/ca/uhn/fhir/parser/JsonParser.java +++ b/hapi-fhir-base/src/main/java/ca/uhn/fhir/parser/JsonParser.java @@ -151,7 +151,7 @@ public class JsonParser extends BaseParser implements IJsonLikeParser { return false; } - private boolean addToHeldExtensions(int valueIdx, List> ext, ArrayList> list, boolean theIsModifier, CompositeChildElement theChildElem) { + private boolean addToHeldExtensions(int valueIdx, List> ext, ArrayList> list, boolean theIsModifier, CompositeChildElement theChildElem, CompositeChildElement theParent) { if (ext.size() > 0) { list.ensureCapacity(valueIdx); while (list.size() <= valueIdx) { @@ -161,7 +161,7 @@ public class JsonParser extends BaseParser implements IJsonLikeParser { list.set(valueIdx, new ArrayList()); } for (IBaseExtension next : ext) { - list.get(valueIdx).add(new HeldExtension(next, theIsModifier, theChildElem)); + list.get(valueIdx).add(new HeldExtension(next, theIsModifier, theChildElem, theParent)); } return true; } @@ -593,7 +593,7 @@ public class JsonParser extends BaseParser implements IJsonLikeParser { if (nextChildElem.getDef().getElementName().equals("extension") || nextChildElem.getDef().getElementName().equals("modifierExtension") || nextChild instanceof RuntimeChildDeclaredExtensionDefinition) { if (!haveWrittenExtensions) { - extractAndWriteExtensionsAsDirectChild(theElement, theEventWriter, myContext.getElementDefinition(theElement.getClass()), theResDef, theResource, nextChildElem); + extractAndWriteExtensionsAsDirectChild(theElement, theEventWriter, myContext.getElementDefinition(theElement.getClass()), theResDef, theResource, nextChildElem, theParent); haveWrittenExtensions = true; } continue; @@ -673,20 +673,20 @@ public class JsonParser extends BaseParser implements IJsonLikeParser { if (primitive) { if (nextValue instanceof ISupportsUndeclaredExtensions) { List ext = ((ISupportsUndeclaredExtensions) nextValue).getUndeclaredExtensions(); - force |= addToHeldExtensions(valueIdx, ext, extensions, false, nextChildElem); + force |= addToHeldExtensions(valueIdx, ext, extensions, false, nextChildElem, theParent); ext = ((ISupportsUndeclaredExtensions) nextValue).getUndeclaredModifierExtensions(); - force |= addToHeldExtensions(valueIdx, ext, modifierExtensions, true, nextChildElem); + force |= addToHeldExtensions(valueIdx, ext, modifierExtensions, true, nextChildElem, theParent); } else { if (nextValue instanceof IBaseHasExtensions) { IBaseHasExtensions element = (IBaseHasExtensions) nextValue; List> ext = element.getExtension(); - force |= addToHeldExtensions(valueIdx, ext, extensions, false, nextChildElem); + force |= addToHeldExtensions(valueIdx, ext, extensions, false, nextChildElem, theParent); } if (nextValue instanceof IBaseHasModifierExtensions) { IBaseHasModifierExtensions element = (IBaseHasModifierExtensions) nextValue; List> ext = element.getModifierExtension(); - force |= addToHeldExtensions(valueIdx, ext, extensions, true, nextChildElem); + force |= addToHeldExtensions(valueIdx, ext, extensions, true, nextChildElem, theParent); } } if (nextValue.hasFormatComment()) { @@ -996,13 +996,14 @@ public class JsonParser extends BaseParser implements IJsonLikeParser { * This is useful only for the two cases where extensions are encoded as direct children (e.g. not in some object * called _name): resource extensions, and extension extensions * @param theChildElem + * @param theParent */ - private void extractAndWriteExtensionsAsDirectChild(IBase theElement, JsonLikeWriter theEventWriter, BaseRuntimeElementDefinition theElementDef, RuntimeResourceDefinition theResDef, IBaseResource theResource, CompositeChildElement theChildElem) throws IOException { + private void extractAndWriteExtensionsAsDirectChild(IBase theElement, JsonLikeWriter theEventWriter, BaseRuntimeElementDefinition theElementDef, RuntimeResourceDefinition theResDef, IBaseResource theResource, CompositeChildElement theChildElem, CompositeChildElement theParent) throws IOException { List extensions = new ArrayList(0); List modifierExtensions = new ArrayList(0); // Undeclared extensions - extractUndeclaredExtensions(theElement, extensions, modifierExtensions, theChildElem); + extractUndeclaredExtensions(theElement, extensions, modifierExtensions, theChildElem, theParent); // Declared extensions if (theElementDef != null) { @@ -1036,7 +1037,7 @@ public class JsonParser extends BaseParser implements IJsonLikeParser { } } - private void extractUndeclaredExtensions(IBase theElement, List extensions, List modifierExtensions, CompositeChildElement theChildElem) { + private void extractUndeclaredExtensions(IBase theElement, List extensions, List modifierExtensions, CompositeChildElement theChildElem, CompositeChildElement theParent) { if (theElement instanceof ISupportsUndeclaredExtensions) { ISupportsUndeclaredExtensions element = (ISupportsUndeclaredExtensions) theElement; List ext = element.getUndeclaredExtensions(); @@ -1044,7 +1045,7 @@ public class JsonParser extends BaseParser implements IJsonLikeParser { if (next == null || next.isEmpty()) { continue; } - extensions.add(new HeldExtension(next, false, theChildElem)); + extensions.add(new HeldExtension(next, false, theChildElem, theParent)); } ext = element.getUndeclaredModifierExtensions(); @@ -1052,7 +1053,7 @@ public class JsonParser extends BaseParser implements IJsonLikeParser { if (next == null || next.isEmpty()) { continue; } - modifierExtensions.add(new HeldExtension(next, true, theChildElem)); + modifierExtensions.add(new HeldExtension(next, true, theChildElem, theParent)); } } else { if (theElement instanceof IBaseHasExtensions) { @@ -1062,7 +1063,7 @@ public class JsonParser extends BaseParser implements IJsonLikeParser { if (next == null || (ElementUtil.isEmpty(next.getValue()) && next.getExtension().isEmpty())) { continue; } - extensions.add(new HeldExtension(next, false, theChildElem)); + extensions.add(new HeldExtension(next, false, theChildElem, theParent)); } } if (theElement instanceof IBaseHasModifierExtensions) { @@ -1072,7 +1073,7 @@ public class JsonParser extends BaseParser implements IJsonLikeParser { if (next == null || next.isEmpty()) { continue; } - modifierExtensions.add(new HeldExtension(next, true, theChildElem)); + modifierExtensions.add(new HeldExtension(next, true, theChildElem, theParent)); } } } @@ -1775,12 +1776,14 @@ public class JsonParser extends BaseParser implements IJsonLikeParser { private boolean myModifier; private IBaseExtension myUndeclaredExtension; private IBase myValue; + private CompositeChildElement myParent; - public HeldExtension(IBaseExtension theUndeclaredExtension, boolean theModifier, CompositeChildElement theChildElem) { + public HeldExtension(IBaseExtension theUndeclaredExtension, boolean theModifier, CompositeChildElement theChildElem, CompositeChildElement theParent) { assert theUndeclaredExtension != null; myUndeclaredExtension = theUndeclaredExtension; myModifier = theModifier; myChildElem = theChildElem; + myParent = theParent; } public HeldExtension(RuntimeChildDeclaredExtensionDefinition theDef, IBase theValue, CompositeChildElement theChildElem) { @@ -1835,10 +1838,10 @@ public class JsonParser extends BaseParser implements IJsonLikeParser { BaseRuntimeElementDefinition def = myDef.getChildElementDefinitionByDatatype(myValue.getClass()); if (def.getChildType() == ChildTypeEnum.RESOURCE_BLOCK) { - extractAndWriteExtensionsAsDirectChild(myValue, theEventWriter, def, theResDef, theResource, myChildElem); + extractAndWriteExtensionsAsDirectChild(myValue, theEventWriter, def, theResDef, theResource, myChildElem, null); } else { String childName = myDef.getChildNameByDatatype(myValue.getClass()); - encodeChildElementToStreamWriter(theResDef, theResource, theEventWriter, myValue, def, childName, false, null, false); + encodeChildElementToStreamWriter(theResDef, theResource, theEventWriter, myValue, def, childName, false, myParent, false); } theEventWriter.endObject(); @@ -1893,7 +1896,7 @@ public class JsonParser extends BaseParser implements IJsonLikeParser { if (childDef == null) { throw new ConfigurationException("Unable to encode extension, unregognized child element type: " + value.getClass().getCanonicalName()); } - encodeChildElementToStreamWriter(theResDef, theResource, theEventWriter, value, childDef, childName, true, null, false); + encodeChildElementToStreamWriter(theResDef, theResource, theEventWriter, value, childDef, childName, true, myParent, false); } // theEventWriter.name(myUndeclaredExtension.get); diff --git a/hapi-fhir-jpaserver-base/src/main/java/ca/uhn/fhir/jpa/dao/BaseHapiFhirResourceDao.java b/hapi-fhir-jpaserver-base/src/main/java/ca/uhn/fhir/jpa/dao/BaseHapiFhirResourceDao.java index 9af90fc0d2c..5f6acb32b2d 100644 --- a/hapi-fhir-jpaserver-base/src/main/java/ca/uhn/fhir/jpa/dao/BaseHapiFhirResourceDao.java +++ b/hapi-fhir-jpaserver-base/src/main/java/ca/uhn/fhir/jpa/dao/BaseHapiFhirResourceDao.java @@ -384,7 +384,7 @@ public abstract class BaseHapiFhirResourceDao extends B * to be reflected in the resource shared with interceptors */ if (!thePerformIndexing) { - incremenetId(theResource, entity, theResource.getIdElement()); + incrementId(theResource, entity, theResource.getIdElement()); } // Notify JPA interceptors @@ -415,7 +415,7 @@ public abstract class BaseHapiFhirResourceDao extends B return outcome; } - private void incremenetId(T theResource, ResourceTable theSavedEntity, IIdType theResourceId) { + private void incrementId(T theResource, ResourceTable theSavedEntity, IIdType theResourceId) { IIdType idType = theResourceId; String newVersion; long newVersionLong; @@ -1131,7 +1131,7 @@ public abstract class BaseHapiFhirResourceDao extends B if (resourceId.hasVersionIdPart() == false) { resourceId = resourceId.withVersion(Long.toString(savedEntity.getVersion())); } - incremenetId(theResource, savedEntity, resourceId); + incrementId(theResource, savedEntity, resourceId); } // Notify interceptors diff --git a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/provider/dstu3/ResourceProviderDstu3Test.java b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/provider/dstu3/ResourceProviderDstu3Test.java index 9fac2f5ab5f..3b3a1e94661 100644 --- a/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/provider/dstu3/ResourceProviderDstu3Test.java +++ b/hapi-fhir-jpaserver-base/src/test/java/ca/uhn/fhir/jpa/provider/dstu3/ResourceProviderDstu3Test.java @@ -175,6 +175,25 @@ public class ResourceProviderDstu3Test extends BaseResourceProviderDstu3Test { myDaoConfig.setAllowMultipleDelete(true); } + @Test + public void testSaveAndRetrieveResourceWithExtension() { + Patient nextPatient = new Patient(); + nextPatient.setId("Patient/B"); + nextPatient + .addExtension() + .setUrl("http://foo") + .setValue(new Reference("Practitioner/A")); + + ourClient.update().resource(nextPatient).execute(); + + Patient p = ourClient.read().resource(Patient.class).withId("B").execute(); + + String encoded = myFhirCtx.newJsonParser().setPrettyPrint(true).encodeResourceToString(p); + ourLog.info(encoded); + + assertThat(encoded, containsString("http://foo")); + } + private void checkParamMissing(String paramName) throws IOException, ClientProtocolException { HttpGet get = new HttpGet(ourServerBase + "/Observation?" + paramName + ":missing=false"); CloseableHttpResponse resp = ourHttpClient.execute(get); @@ -1549,12 +1568,11 @@ public class ResourceProviderDstu3Test extends BaseResourceProviderDstu3Test { } assertEquals(null, responseBundle.getLink("next")); - + assertThat(ids, hasItem("List/A161444")); assertThat(ids, hasItem("List/A161468")); assertThat(ids, hasItem("List/A161500")); - ourLog.info("Expected {} - {}", allIds.size(), allIds); ourLog.info("Actual {} - {}", ids.size(), ids); assertEquals(allIds, ids); @@ -1726,7 +1744,7 @@ public class ResourceProviderDstu3Test extends BaseResourceProviderDstu3Test { preDates.add(new Date()); Thread.sleep(100); patient.setId(id); - patient.getName().get(0).getFamilyElement().setValue(methodName + "_i"+i); + patient.getName().get(0).getFamilyElement().setValue(methodName + "_i" + i); ids.add(myPatientDao.update(patient, mySrd).getId().toUnqualified().getValue()); } @@ -3149,7 +3167,7 @@ public class ResourceProviderDstu3Test extends BaseResourceProviderDstu3Test { myPatientDao.create(patient, mySrd).getId().toUnqualifiedVersionless(); // should be subject._id - HttpGet httpPost = new HttpGet(ourServerBase + "/Observation?subject.id=FOO"); + HttpGet httpPost = new HttpGet(ourServerBase + "/Observation?subject.id=FOO"); CloseableHttpResponse resp = ourHttpClient.execute(httpPost); try { @@ -3162,7 +3180,7 @@ public class ResourceProviderDstu3Test extends BaseResourceProviderDstu3Test { } ourLog.info("Outgoing post: {}", httpPost); } - + /** * See #411 * diff --git a/hapi-fhir-structures-dstu3/src/test/java/ca/uhn/fhir/parser/JsonParserDstu3Test.java b/hapi-fhir-structures-dstu3/src/test/java/ca/uhn/fhir/parser/JsonParserDstu3Test.java index edf32a2eb9f..ac163282b6e 100644 --- a/hapi-fhir-structures-dstu3/src/test/java/ca/uhn/fhir/parser/JsonParserDstu3Test.java +++ b/hapi-fhir-structures-dstu3/src/test/java/ca/uhn/fhir/parser/JsonParserDstu3Test.java @@ -98,6 +98,7 @@ public class JsonParserDstu3Test { assertEquals("Found incorrect type for element subject - Expected OBJECT and found SCALAR (STRING)", e.getMessage()); } } + /** * See #563 @@ -116,47 +117,6 @@ public class JsonParserDstu3Test { } } - @Test - public void testOverrideResourceIdWithBundleEntryFullUrlDisabled_ConfiguredOnFhirContext() { - try { - String tmp = "{\"resourceType\":\"Bundle\",\"entry\":[{\"fullUrl\":\"http://lalaland.org/patient/pat1\",\"resource\":{\"resourceType\":\"Patient\",\"id\":\"patxuzos\"}}]}"; - ourCtx.getParserOptions().setOverrideResourceIdWithBundleEntryFullUrl(false); - Bundle bundle = (Bundle) ourCtx.newJsonParser().parseResource(tmp); - assertEquals(1, bundle.getEntry().size()); - { - Patient o1 = (Patient) bundle.getEntry().get(0).getResource(); - IIdType o1Id = o1.getIdElement(); - assertFalse(o1Id.hasBaseUrl()); - assertEquals("Patient", o1Id.getResourceType()); - assertEquals("patxuzos", o1Id.getIdPart()); - assertFalse(o1Id.hasVersionIdPart()); - } - } finally { - // ensure we cleanup ourCtx so other tests continue to work - ourCtx = FhirContext.forDstu3(); - } - } - - @Test - public void testOverrideResourceIdWithBundleEntryFullUrlDisabled_ConfiguredOnParser() { - try { - String tmp = "{\"resourceType\":\"Bundle\",\"entry\":[{\"fullUrl\":\"http://lalaland.org/patient/pat1\",\"resource\":{\"resourceType\":\"Patient\",\"id\":\"patxuzos\"}}]}"; - Bundle bundle = (Bundle) ourCtx.newJsonParser().setOverrideResourceIdWithBundleEntryFullUrl(false).parseResource(tmp); - assertEquals(1, bundle.getEntry().size()); - { - Patient o1 = (Patient) bundle.getEntry().get(0).getResource(); - IIdType o1Id = o1.getIdElement(); - assertFalse(o1Id.hasBaseUrl()); - assertEquals("Patient", o1Id.getResourceType()); - assertEquals("patxuzos", o1Id.getIdPart()); - assertFalse(o1Id.hasVersionIdPart()); - } - } finally { - // ensure we cleanup ourCtx so other tests continue to work - ourCtx = FhirContext.forDstu3(); - } - } - /** * See #544 */ @@ -184,81 +144,73 @@ public class JsonParserDstu3Test { assertNotNull(subject); assertEquals("FAMILY", subject.getNameFirstRep().getFamily()); } - + /** + * Test for the url generated based on the server config + */ @Test - public void testIncorrectJsonTypesIdAndArray() { - - // ID should be a String and communication should be an Array - String input = "{\"resourceType\": \"Patient\",\n" + - " \"id\": 123,\n" + - " \"communication\": {\n" + - " \"language\": {\n" + - " \"text\": \"Hindi\"\n" + - " },\n" + - " \"preferred\": true\n" + - " }\n" + - "}"; + public void testCustomUrlExtension() { + final String expected = "{\"resourceType\":\"Patient\",\"extension\":[{\"url\":\"http://www.example.com/petname\",\"valueString\":\"myName\"}]}"; - IParser p = ourCtx.newJsonParser(); - - IParserErrorHandler errorHandler = mock(IParserErrorHandler.class); - p.setParserErrorHandler(errorHandler); - Patient patient = (Patient) p.parseResource(input); - - ArgumentCaptor elementName = ArgumentCaptor.forClass(String.class); - ArgumentCaptor found = ArgumentCaptor.forClass(ValueType.class); - ArgumentCaptor expected = ArgumentCaptor.forClass(ValueType.class); - ArgumentCaptor expectedScalarType = ArgumentCaptor.forClass(ScalarType.class); - ArgumentCaptor foundScalarType = ArgumentCaptor.forClass(ScalarType.class); - verify(errorHandler, times(2)).incorrectJsonType(any(IParseLocation.class), elementName.capture(), expected.capture(), expectedScalarType.capture(), found.capture(), foundScalarType.capture()); - - assertEquals(ValueType.SCALAR, found.getAllValues().get(0)); - assertEquals(ValueType.SCALAR, expected.getAllValues().get(0)); - assertEquals(ScalarType.NUMBER, foundScalarType.getAllValues().get(0)); - assertEquals(ScalarType.STRING, expectedScalarType.getAllValues().get(0)); - - assertEquals(ValueType.OBJECT, found.getAllValues().get(1)); - assertEquals(ValueType.ARRAY, expected.getAllValues().get(1)); - assertEquals(null, foundScalarType.getAllValues().get(1)); - assertEquals(null, expectedScalarType.getAllValues().get(1)); - - assertEquals("123", patient.getIdElement().getIdPart()); - assertEquals("Hindi", patient.getCommunicationFirstRep().getLanguage().getText()); + final MyPatientWithCustomUrlExtension patient = new MyPatientWithCustomUrlExtension(); + patient.setPetName(new StringType("myName")); + + final IParser jsonParser = ourCtx.newJsonParser(); + jsonParser.setServerBaseUrl("http://www.example.com"); + + final String parsedPatient = jsonParser.encodeResourceToString(patient); + System.out.println(parsedPatient); + assertEquals(expected, parsedPatient); + + // Parse with string + MyPatientWithCustomUrlExtension newPatient = jsonParser.parseResource(MyPatientWithCustomUrlExtension.class, parsedPatient); + assertEquals("myName", newPatient.getPetName().getValue()); + + // Parse with stream + newPatient = jsonParser.parseResource(MyPatientWithCustomUrlExtension.class, new StringReader(parsedPatient)); + assertEquals("myName", newPatient.getPetName().getValue()); + + //Check no NPE if base server not configure + newPatient = ourCtx.newJsonParser().parseResource(MyPatientWithCustomUrlExtension.class, new StringReader(parsedPatient)); + assertNull("myName", newPatient.getPetName().getValue()); + assertEquals("myName", ((StringType) newPatient.getExtensionsByUrl("http://www.example.com/petname").get(0).getValue()).getValue()); } @Test - public void testIncorrectJsonTypesNone() { - - // ID should be a String and communication should be an Array - String input = "{\"resourceType\": \"Patient\",\n" + - " \"id\": \"123\",\n" + - " \"communication\": [{\n" + - " \"language\": {\n" + - " \"text\": \"Hindi\"\n" + - " },\n" + - " \"preferred\": true\n" + - " }]\n" + - "}"; + public void testCustomUrlExtensioninBundle() { + final String expected = "{\"resourceType\":\"Bundle\",\"entry\":[{\"resource\":{\"resourceType\":\"Patient\",\"extension\":[{\"url\":\"http://www.example.com/petname\",\"valueString\":\"myName\"}]}}]}"; + + final MyPatientWithCustomUrlExtension patient = new MyPatientWithCustomUrlExtension(); + patient.setPetName(new StringType("myName")); + + final Bundle bundle = new Bundle(); + final BundleEntryComponent entry = new BundleEntryComponent(); + entry.setResource(patient); + bundle.addEntry(entry); + + final IParser jsonParser = ourCtx.newJsonParser(); + jsonParser.setServerBaseUrl("http://www.example.com"); + + final String parsedBundle = jsonParser.encodeResourceToString(bundle); + System.out.println(parsedBundle); + assertEquals(expected, parsedBundle); + + // Parse with string + Bundle newBundle = jsonParser.parseResource(Bundle.class, parsedBundle); + assertNotNull(newBundle); + assertEquals(1, newBundle.getEntry().size()); + Patient newPatient = (Patient) newBundle.getEntry().get(0).getResource(); + assertEquals("myName", ((StringType) newPatient.getExtensionsByUrl("http://www.example.com/petname").get(0).getValue()).getValue()); + + // Parse with stream + newBundle = jsonParser.parseResource(Bundle.class, new StringReader(parsedBundle)); + assertNotNull(newBundle); + assertEquals(1, newBundle.getEntry().size()); + newPatient = (Patient) newBundle.getEntry().get(0).getResource(); + assertEquals("myName", ((StringType) newPatient.getExtensionsByUrl("http://www.example.com/petname").get(0).getValue()).getValue()); - IParser p = ourCtx.newJsonParser(); - - IParserErrorHandler errorHandler = mock(IParserErrorHandler.class); - p.setParserErrorHandler(errorHandler); - Patient patient = (Patient) p.parseResource(input); - - ArgumentCaptor elementName = ArgumentCaptor.forClass(String.class); - ArgumentCaptor found = ArgumentCaptor.forClass(ValueType.class); - ArgumentCaptor expected = ArgumentCaptor.forClass(ValueType.class); - ArgumentCaptor expectedScalarType = ArgumentCaptor.forClass(ScalarType.class); - ArgumentCaptor foundScalarType = ArgumentCaptor.forClass(ScalarType.class); - verify(errorHandler, times(0)).incorrectJsonType(any(IParseLocation.class), elementName.capture(), expected.capture(), expectedScalarType.capture(), found.capture(), foundScalarType.capture()); - - assertEquals("123", patient.getIdElement().getIdPart()); - assertEquals("Hindi", patient.getCommunicationFirstRep().getLanguage().getText()); } - /** * See #276 */ @@ -285,81 +237,7 @@ public class JsonParserDstu3Test { assertEquals(3, countMatches(encoded, "resourceType")); } - /** - * #480 - */ - @Test - public void testEncodeEmptyValue() { - QuestionnaireResponse qr = new QuestionnaireResponse(); - qr.setId("123"); - qr.getAuthoredElement().setValueAsString(""); - qr.getItemFirstRep().setLinkIdElement(new StringType()); - qr.getItemFirstRep().addItem().setLinkIdElement(new StringType("")); - qr.getItemFirstRep().addItem().setLinkIdElement(new StringType("LINKID")); - - String encoded = ourCtx.newJsonParser().encodeResourceToString(qr); - ourLog.info(encoded); - - assertThat(encoded, stringContainsInOrder("123")); - assertThat(encoded, not(stringContainsInOrder("\"\""))); - assertThat(encoded, not(stringContainsInOrder("null"))); - } - - /** - * #480 - */ - @Test - public void testParseEmptyValue() { - String input = "{\"resourceType\":\"QuestionnaireResponse\",\"id\":\"123\",\"authored\":\"\",\"group\":{\"linkId\":\"\"}}"; - IParser parser = ourCtx.newJsonParser(); - - parser.setParserErrorHandler(new LenientErrorHandler().setErrorOnInvalidValue(false)); - QuestionnaireResponse qr = parser.parseResource(QuestionnaireResponse.class, input); - assertEquals("QuestionnaireResponse/123", qr.getIdElement().getValue()); - assertEquals(null, qr.getAuthored()); - assertEquals(null, qr.getAuthoredElement().getValue()); - assertEquals(null, qr.getAuthoredElement().getValueAsString()); - assertEquals(null, qr.getItemFirstRep().getLinkId()); - assertEquals(null, qr.getItemFirstRep().getLinkIdElement().getValue()); - } - - /** - * See #477 - */ - @Test - public void testUnexpectedElementsWithUnderscoreAtStartOfName() throws Exception { - String input = IOUtils.toString(JsonParserDstu3Test.class.getResourceAsStream("/bug477.json"), StandardCharsets.UTF_8); - - IParserErrorHandler errorHandler = mock(IParserErrorHandler.class); - - // Do it once without the custom error handler just for the logging - IParser p = ourCtx.newJsonParser(); - p.parseResource(Patient.class, input); - - p = ourCtx.newJsonParser(); - p.setParserErrorHandler(errorHandler); - - Patient parsed = p.parseResource(Patient.class, input); - assertEquals("1", parsed.getIdElement().getIdPart()); - - ArgumentCaptor elementName = ArgumentCaptor.forClass(String.class); - ArgumentCaptor expected = ArgumentCaptor.forClass(ValueType.class); - ArgumentCaptor actual = ArgumentCaptor.forClass(ValueType.class); - ArgumentCaptor expectedScalar = ArgumentCaptor.forClass(ScalarType.class); - ArgumentCaptor actualScalar = ArgumentCaptor.forClass(ScalarType.class); - verify(errorHandler, atLeastOnce()).incorrectJsonType(Mockito.any(IParseLocation.class), elementName.capture(), expected.capture(), expectedScalar.capture(), actual.capture(), actualScalar.capture()); - verify(errorHandler, atLeastOnce()).incorrectJsonType(Mockito.any(IParseLocation.class), Mockito.eq("_id"), Mockito.eq(ValueType.OBJECT), expectedScalar.capture(), Mockito.eq(ValueType.SCALAR), actualScalar.capture()); - verify(errorHandler, atLeastOnce()).incorrectJsonType(Mockito.any(IParseLocation.class), Mockito.eq("__v"), Mockito.eq(ValueType.OBJECT), expectedScalar.capture(), Mockito.eq(ValueType.SCALAR), actualScalar.capture()); - verify(errorHandler, atLeastOnce()).incorrectJsonType(Mockito.any(IParseLocation.class), Mockito.eq("_status"), Mockito.eq(ValueType.OBJECT), expectedScalar.capture(), Mockito.eq(ValueType.SCALAR), actualScalar.capture()); - - assertEquals("_id", elementName.getAllValues().get(0)); - assertEquals(ValueType.OBJECT, expected.getAllValues().get(0)); - assertEquals(ValueType.SCALAR, actual.getAllValues().get(0)); - assertEquals(null, expectedScalar.getAllValues().get(0)); - assertEquals(null, actualScalar.getAllValues().get(0)); - } - @Test public void testEncodeAndParseExtensions() throws Exception { @@ -445,7 +323,7 @@ public class JsonParserDstu3Test { assertEquals("CHILD", ((StringType) given2ext2.getValue()).getValue()); } - + @Test public void testEncodeAndParseMetaProfileAndTags() { Patient p = new Patient(); @@ -524,6 +402,7 @@ public class JsonParserDstu3Test { assertEquals("sec_label2", tagList.get(1).getDisplay()); } + /** * See #336 */ @@ -740,6 +619,26 @@ public class JsonParserDstu3Test { assertThat(encoded, not(containsString("Label"))); } + /** + * #480 + */ + @Test + public void testEncodeEmptyValue() { + QuestionnaireResponse qr = new QuestionnaireResponse(); + qr.setId("123"); + qr.getAuthoredElement().setValueAsString(""); + qr.getItemFirstRep().setLinkIdElement(new StringType()); + qr.getItemFirstRep().addItem().setLinkIdElement(new StringType("")); + qr.getItemFirstRep().addItem().setLinkIdElement(new StringType("LINKID")); + + String encoded = ourCtx.newJsonParser().encodeResourceToString(qr); + ourLog.info(encoded); + + assertThat(encoded, stringContainsInOrder("123")); + assertThat(encoded, not(stringContainsInOrder("\"\""))); + assertThat(encoded, not(stringContainsInOrder("null"))); + } + @Test public void testEncodeExtendedInfrastructureComponent() { IParser parser = ourCtx.newJsonParser(); @@ -794,6 +693,25 @@ public class JsonParserDstu3Test { } + @Test + public void testEncodeExtensionOnRoot() { + Patient p = new Patient(); + p.setId("Patient/B"); + p + .addExtension() + .setUrl("http://foo") + .setValue(new Reference("Practitioner/A")); + + IParser parser = ourCtx.newJsonParser().setPrettyPrint(true); + parser.setDontEncodeElements(new HashSet(Arrays.asList("*.id", "*.meta"))); + + String encoded = parser.encodeResourceToString(p); + ourLog.info(encoded); + + assertThat(encoded, containsString("http://foo")); + assertThat(encoded, containsString("Practitioner/A")); + } + @Test public void testEncodeExtensionUndeclaredNonModifier() { Observation obs = new Observation(); @@ -1387,6 +1305,98 @@ public class JsonParserDstu3Test { assertEquals("{\"resourceType\":\"Observation\",\"valueQuantity\":{\"value\":0.0000000000000001}}", str); } + @Test + public void testIncorrectJsonTypesIdAndArray() { + + // ID should be a String and communication should be an Array + String input = "{\"resourceType\": \"Patient\",\n" + + " \"id\": 123,\n" + + " \"communication\": {\n" + + " \"language\": {\n" + + " \"text\": \"Hindi\"\n" + + " },\n" + + " \"preferred\": true\n" + + " }\n" + + "}"; + + IParser p = ourCtx.newJsonParser(); + + IParserErrorHandler errorHandler = mock(IParserErrorHandler.class); + p.setParserErrorHandler(errorHandler); + Patient patient = (Patient) p.parseResource(input); + + ArgumentCaptor elementName = ArgumentCaptor.forClass(String.class); + ArgumentCaptor found = ArgumentCaptor.forClass(ValueType.class); + ArgumentCaptor expected = ArgumentCaptor.forClass(ValueType.class); + ArgumentCaptor expectedScalarType = ArgumentCaptor.forClass(ScalarType.class); + ArgumentCaptor foundScalarType = ArgumentCaptor.forClass(ScalarType.class); + verify(errorHandler, times(2)).incorrectJsonType(any(IParseLocation.class), elementName.capture(), expected.capture(), expectedScalarType.capture(), found.capture(), foundScalarType.capture()); + + assertEquals(ValueType.SCALAR, found.getAllValues().get(0)); + assertEquals(ValueType.SCALAR, expected.getAllValues().get(0)); + assertEquals(ScalarType.NUMBER, foundScalarType.getAllValues().get(0)); + assertEquals(ScalarType.STRING, expectedScalarType.getAllValues().get(0)); + + assertEquals(ValueType.OBJECT, found.getAllValues().get(1)); + assertEquals(ValueType.ARRAY, expected.getAllValues().get(1)); + assertEquals(null, foundScalarType.getAllValues().get(1)); + assertEquals(null, expectedScalarType.getAllValues().get(1)); + + assertEquals("123", patient.getIdElement().getIdPart()); + assertEquals("Hindi", patient.getCommunicationFirstRep().getLanguage().getText()); + } + + @Test + public void testIncorrectJsonTypesNone() { + + // ID should be a String and communication should be an Array + String input = "{\"resourceType\": \"Patient\",\n" + + " \"id\": \"123\",\n" + + " \"communication\": [{\n" + + " \"language\": {\n" + + " \"text\": \"Hindi\"\n" + + " },\n" + + " \"preferred\": true\n" + + " }]\n" + + "}"; + + IParser p = ourCtx.newJsonParser(); + + IParserErrorHandler errorHandler = mock(IParserErrorHandler.class); + p.setParserErrorHandler(errorHandler); + Patient patient = (Patient) p.parseResource(input); + + ArgumentCaptor elementName = ArgumentCaptor.forClass(String.class); + ArgumentCaptor found = ArgumentCaptor.forClass(ValueType.class); + ArgumentCaptor expected = ArgumentCaptor.forClass(ValueType.class); + ArgumentCaptor expectedScalarType = ArgumentCaptor.forClass(ScalarType.class); + ArgumentCaptor foundScalarType = ArgumentCaptor.forClass(ScalarType.class); + verify(errorHandler, times(0)).incorrectJsonType(any(IParseLocation.class), elementName.capture(), expected.capture(), expectedScalarType.capture(), found.capture(), foundScalarType.capture()); + + assertEquals("123", patient.getIdElement().getIdPart()); + assertEquals("Hindi", patient.getCommunicationFirstRep().getLanguage().getText()); + } + + @Test + public void testInvalidDateTimeValueInvalid() throws Exception { + IParserErrorHandler errorHandler = mock(IParserErrorHandler.class); + + String res = "{ \"resourceType\": \"Observation\", \"valueDateTime\": \"foo\" }"; + IParser parser = ourCtx.newJsonParser(); + parser.setParserErrorHandler(errorHandler); + Observation parsed = parser.parseResource(Observation.class, res); + + assertEquals(null, parsed.getValueDateTimeType().getValue()); + assertEquals("foo", parsed.getValueDateTimeType().getValueAsString()); + + ArgumentCaptor msgCaptor = ArgumentCaptor.forClass(String.class); + verify(errorHandler, times(1)).invalidValue(isNull(IParseLocation.class), eq("foo"), msgCaptor.capture()); + assertEquals("Invalid date/time format: \"foo\"", msgCaptor.getValue()); + + String encoded = ourCtx.newJsonParser().encodeResourceToString(parsed); + assertEquals("{\"resourceType\":\"Observation\",\"valueDateTime\":\"foo\"}", encoded); + } + /** * #516 */ @@ -1439,26 +1449,6 @@ public class JsonParserDstu3Test { assertEquals("{\"resourceType\":\"Patient\",\"gender\":\"foo\"}", encoded); } - @Test - public void testInvalidDateTimeValueInvalid() throws Exception { - IParserErrorHandler errorHandler = mock(IParserErrorHandler.class); - - String res = "{ \"resourceType\": \"Observation\", \"valueDateTime\": \"foo\" }"; - IParser parser = ourCtx.newJsonParser(); - parser.setParserErrorHandler(errorHandler); - Observation parsed = parser.parseResource(Observation.class, res); - - assertEquals(null, parsed.getValueDateTimeType().getValue()); - assertEquals("foo", parsed.getValueDateTimeType().getValueAsString()); - - ArgumentCaptor msgCaptor = ArgumentCaptor.forClass(String.class); - verify(errorHandler, times(1)).invalidValue(isNull(IParseLocation.class), eq("foo"), msgCaptor.capture()); - assertEquals("Invalid date/time format: \"foo\"", msgCaptor.getValue()); - - String encoded = ourCtx.newJsonParser().encodeResourceToString(parsed); - assertEquals("{\"resourceType\":\"Observation\",\"valueDateTime\":\"foo\"}", encoded); - } - /** * #65 */ @@ -1533,6 +1523,47 @@ public class JsonParserDstu3Test { assertThat(ourCtx.newJsonParser().setOmitResourceId(true).encodeResourceToString(p), not(containsString("123"))); } + @Test + public void testOverrideResourceIdWithBundleEntryFullUrlDisabled_ConfiguredOnFhirContext() { + try { + String tmp = "{\"resourceType\":\"Bundle\",\"entry\":[{\"fullUrl\":\"http://lalaland.org/patient/pat1\",\"resource\":{\"resourceType\":\"Patient\",\"id\":\"patxuzos\"}}]}"; + ourCtx.getParserOptions().setOverrideResourceIdWithBundleEntryFullUrl(false); + Bundle bundle = (Bundle) ourCtx.newJsonParser().parseResource(tmp); + assertEquals(1, bundle.getEntry().size()); + { + Patient o1 = (Patient) bundle.getEntry().get(0).getResource(); + IIdType o1Id = o1.getIdElement(); + assertFalse(o1Id.hasBaseUrl()); + assertEquals("Patient", o1Id.getResourceType()); + assertEquals("patxuzos", o1Id.getIdPart()); + assertFalse(o1Id.hasVersionIdPart()); + } + } finally { + // ensure we cleanup ourCtx so other tests continue to work + ourCtx = FhirContext.forDstu3(); + } + } + + @Test + public void testOverrideResourceIdWithBundleEntryFullUrlDisabled_ConfiguredOnParser() { + try { + String tmp = "{\"resourceType\":\"Bundle\",\"entry\":[{\"fullUrl\":\"http://lalaland.org/patient/pat1\",\"resource\":{\"resourceType\":\"Patient\",\"id\":\"patxuzos\"}}]}"; + Bundle bundle = (Bundle) ourCtx.newJsonParser().setOverrideResourceIdWithBundleEntryFullUrl(false).parseResource(tmp); + assertEquals(1, bundle.getEntry().size()); + { + Patient o1 = (Patient) bundle.getEntry().get(0).getResource(); + IIdType o1Id = o1.getIdElement(); + assertFalse(o1Id.hasBaseUrl()); + assertEquals("Patient", o1Id.getResourceType()); + assertEquals("patxuzos", o1Id.getIdPart()); + assertFalse(o1Id.hasVersionIdPart()); + } + } finally { + // ensure we cleanup ourCtx so other tests continue to work + ourCtx = FhirContext.forDstu3(); + } + } + @Test @Ignore public void testParseAndEncodeBundle() throws Exception { @@ -1872,6 +1903,25 @@ public class JsonParserDstu3Test { assertEquals("patient family", p.getName().get(0).getFamilyElement().getValue()); } + /** + * #480 + */ + @Test + public void testParseEmptyValue() { + String input = "{\"resourceType\":\"QuestionnaireResponse\",\"id\":\"123\",\"authored\":\"\",\"group\":{\"linkId\":\"\"}}"; + IParser parser = ourCtx.newJsonParser(); + + parser.setParserErrorHandler(new LenientErrorHandler().setErrorOnInvalidValue(false)); + QuestionnaireResponse qr = parser.parseResource(QuestionnaireResponse.class, input); + + assertEquals("QuestionnaireResponse/123", qr.getIdElement().getValue()); + assertEquals(null, qr.getAuthored()); + assertEquals(null, qr.getAuthoredElement().getValue()); + assertEquals(null, qr.getAuthoredElement().getValueAsString()); + assertEquals(null, qr.getItemFirstRep().getLinkId()); + assertEquals(null, qr.getItemFirstRep().getLinkIdElement().getValue()); + } + /** * See #335 */ @@ -2224,6 +2274,42 @@ public class JsonParserDstu3Test { Assert.assertThat(message, containsString("contained")); } + /** + * See #477 + */ + @Test + public void testUnexpectedElementsWithUnderscoreAtStartOfName() throws Exception { + String input = IOUtils.toString(JsonParserDstu3Test.class.getResourceAsStream("/bug477.json"), StandardCharsets.UTF_8); + + IParserErrorHandler errorHandler = mock(IParserErrorHandler.class); + + // Do it once without the custom error handler just for the logging + IParser p = ourCtx.newJsonParser(); + p.parseResource(Patient.class, input); + + p = ourCtx.newJsonParser(); + p.setParserErrorHandler(errorHandler); + + Patient parsed = p.parseResource(Patient.class, input); + assertEquals("1", parsed.getIdElement().getIdPart()); + + ArgumentCaptor elementName = ArgumentCaptor.forClass(String.class); + ArgumentCaptor expected = ArgumentCaptor.forClass(ValueType.class); + ArgumentCaptor actual = ArgumentCaptor.forClass(ValueType.class); + ArgumentCaptor expectedScalar = ArgumentCaptor.forClass(ScalarType.class); + ArgumentCaptor actualScalar = ArgumentCaptor.forClass(ScalarType.class); + verify(errorHandler, atLeastOnce()).incorrectJsonType(Mockito.any(IParseLocation.class), elementName.capture(), expected.capture(), expectedScalar.capture(), actual.capture(), actualScalar.capture()); + verify(errorHandler, atLeastOnce()).incorrectJsonType(Mockito.any(IParseLocation.class), Mockito.eq("_id"), Mockito.eq(ValueType.OBJECT), expectedScalar.capture(), Mockito.eq(ValueType.SCALAR), actualScalar.capture()); + verify(errorHandler, atLeastOnce()).incorrectJsonType(Mockito.any(IParseLocation.class), Mockito.eq("__v"), Mockito.eq(ValueType.OBJECT), expectedScalar.capture(), Mockito.eq(ValueType.SCALAR), actualScalar.capture()); + verify(errorHandler, atLeastOnce()).incorrectJsonType(Mockito.any(IParseLocation.class), Mockito.eq("_status"), Mockito.eq(ValueType.OBJECT), expectedScalar.capture(), Mockito.eq(ValueType.SCALAR), actualScalar.capture()); + + assertEquals("_id", elementName.getAllValues().get(0)); + assertEquals(ValueType.OBJECT, expected.getAllValues().get(0)); + assertEquals(ValueType.SCALAR, actual.getAllValues().get(0)); + assertEquals(null, expectedScalar.getAllValues().get(0)); + assertEquals(null, actualScalar.getAllValues().get(0)); + } + @Test public void testValidateCustomStructure() throws Exception { @@ -2247,72 +2333,6 @@ public class JsonParserDstu3Test { assertTrue(result.isSuccessful()); } - /** - * Test for the url generated based on the server config - */ - @Test - public void testCustomUrlExtension() { - final String expected = "{\"resourceType\":\"Patient\",\"extension\":[{\"url\":\"http://www.example.com/petname\",\"valueString\":\"myName\"}]}"; - - final MyPatientWithCustomUrlExtension patient = new MyPatientWithCustomUrlExtension(); - patient.setPetName(new StringType("myName")); - - final IParser jsonParser = ourCtx.newJsonParser(); - jsonParser.setServerBaseUrl("http://www.example.com"); - - final String parsedPatient = jsonParser.encodeResourceToString(patient); - System.out.println(parsedPatient); - assertEquals(expected, parsedPatient); - - // Parse with string - MyPatientWithCustomUrlExtension newPatient = jsonParser.parseResource(MyPatientWithCustomUrlExtension.class, parsedPatient); - assertEquals("myName", newPatient.getPetName().getValue()); - - // Parse with stream - newPatient = jsonParser.parseResource(MyPatientWithCustomUrlExtension.class, new StringReader(parsedPatient)); - assertEquals("myName", newPatient.getPetName().getValue()); - - //Check no NPE if base server not configure - newPatient = ourCtx.newJsonParser().parseResource(MyPatientWithCustomUrlExtension.class, new StringReader(parsedPatient)); - assertNull("myName", newPatient.getPetName().getValue()); - assertEquals("myName", ((StringType) newPatient.getExtensionsByUrl("http://www.example.com/petname").get(0).getValue()).getValue()); - } - - @Test - public void testCustomUrlExtensioninBundle() { - final String expected = "{\"resourceType\":\"Bundle\",\"entry\":[{\"resource\":{\"resourceType\":\"Patient\",\"extension\":[{\"url\":\"http://www.example.com/petname\",\"valueString\":\"myName\"}]}}]}"; - - final MyPatientWithCustomUrlExtension patient = new MyPatientWithCustomUrlExtension(); - patient.setPetName(new StringType("myName")); - - final Bundle bundle = new Bundle(); - final BundleEntryComponent entry = new BundleEntryComponent(); - entry.setResource(patient); - bundle.addEntry(entry); - - final IParser jsonParser = ourCtx.newJsonParser(); - jsonParser.setServerBaseUrl("http://www.example.com"); - - final String parsedBundle = jsonParser.encodeResourceToString(bundle); - System.out.println(parsedBundle); - assertEquals(expected, parsedBundle); - - // Parse with string - Bundle newBundle = jsonParser.parseResource(Bundle.class, parsedBundle); - assertNotNull(newBundle); - assertEquals(1, newBundle.getEntry().size()); - Patient newPatient = (Patient) newBundle.getEntry().get(0).getResource(); - assertEquals("myName", ((StringType) newPatient.getExtensionsByUrl("http://www.example.com/petname").get(0).getValue()).getValue()); - - // Parse with stream - newBundle = jsonParser.parseResource(Bundle.class, new StringReader(parsedBundle)); - assertNotNull(newBundle); - assertEquals(1, newBundle.getEntry().size()); - newPatient = (Patient) newBundle.getEntry().get(0).getResource(); - assertEquals("myName", ((StringType) newPatient.getExtensionsByUrl("http://www.example.com/petname").get(0).getValue()).getValue()); - - } - @AfterClass public static void afterClassClearContext() { TestUtil.clearAllStaticFieldsForUnitTest(); diff --git a/hapi-fhir-structures-dstu3/src/test/java/ca/uhn/fhir/parser/XmlParserDstu3Test.java b/hapi-fhir-structures-dstu3/src/test/java/ca/uhn/fhir/parser/XmlParserDstu3Test.java index 081b306aacf..e782d8913c1 100644 --- a/hapi-fhir-structures-dstu3/src/test/java/ca/uhn/fhir/parser/XmlParserDstu3Test.java +++ b/hapi-fhir-structures-dstu3/src/test/java/ca/uhn/fhir/parser/XmlParserDstu3Test.java @@ -69,17 +69,1917 @@ import ca.uhn.fhir.rest.server.Constants; import ca.uhn.fhir.util.TestUtil; public class XmlParserDstu3Test { - private static FhirContext ourCtx = FhirContext.forDstu3(); - private static final org.slf4j.Logger ourLog = org.slf4j.LoggerFactory.getLogger(XmlParserDstu3Test.class); + private static FhirContext ourCtx = FhirContext.forDstu3(); + private static final org.slf4j.Logger ourLog = org.slf4j.LoggerFactory.getLogger(XmlParserDstu3Test.class); + + @After + public void after() { + if (ourCtx == null) { + ourCtx = FhirContext.forDstu3(); + } + ourCtx.setNarrativeGenerator(null); + } + + /** + * See #544 + */ + @Test + public void testBundleStitchReferencesByUuid() throws Exception { + Bundle bundle = new Bundle(); + + DocumentManifest dm = new DocumentManifest(); + dm.getSubject().setReference("urn:uuid:96e85cca-9797-45d6-834a-c4eb27f331d3"); + bundle.addEntry().setResource(dm); + + Patient patient = new Patient(); + patient.addName().setFamily("FAMILY"); + bundle.addEntry().setResource(patient).setFullUrl("urn:uuid:96e85cca-9797-45d6-834a-c4eb27f331d3"); + + String encoded = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(bundle); + ourLog.info(encoded); + + bundle = ourCtx.newXmlParser().parseResource(Bundle.class, encoded); + dm = (DocumentManifest) bundle.getEntry().get(0).getResource(); + + assertEquals("urn:uuid:96e85cca-9797-45d6-834a-c4eb27f331d3", dm.getSubject().getReference()); + + Patient subject = (Patient) dm.getSubject().getResource(); + assertNotNull(subject); + assertEquals("FAMILY", subject.getNameFirstRep().getFamily()); + } + + @Test + public void testBundleWithBinary() { + + String bundle = "\n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + ""; + + Bundle b = ourCtx.newXmlParser().parseResource(Bundle.class, bundle); + assertEquals(1, b.getEntry().size()); + + Binary bin = (Binary) b.getEntry().get(0).getResource(); + assertArrayEquals(new byte[] { 1, 2, 3, 4 }, bin.getContent()); + + } + + @Test + public void testContainedResourceInExtensionUndeclared() { + Patient p = new Patient(); + p.addName().setFamily("PATIENT"); + + Organization o = new Organization(); + o.setName("ORG"); + p.addExtension(new Extension("urn:foo", new Reference(o))); + + String str = ourCtx.newXmlParser().encodeResourceToString(p); + ourLog.info(str); + + p = ourCtx.newXmlParser().parseResource(Patient.class, str); + assertEquals("PATIENT", p.getName().get(0).getFamily()); + + List exts = p.getExtensionsByUrl("urn:foo"); + assertEquals(1, exts.size()); + Reference rr = (Reference) exts.get(0).getValue(); + o = (Organization) rr.getResource(); + assertEquals("ORG", o.getName()); + } + + @Test(expected = DataFormatException.class) + public void testContainedResourceWithNoId() throws IOException { + String string = IOUtils.toString(getClass().getResourceAsStream("/bundle_with_contained_with_no_id.xml"), StandardCharsets.UTF_8); + + IParser parser = ourCtx.newXmlParser(); + parser.setParserErrorHandler(new StrictErrorHandler()); + parser.parseResource(Bundle.class, string); + } + + @Test() + public void testContainedResourceWithNoIdLenient() throws IOException { + String string = IOUtils.toString(getClass().getResourceAsStream("/bundle_with_contained_with_no_id.xml"), StandardCharsets.UTF_8); + + IParser parser = ourCtx.newXmlParser(); + parser.setParserErrorHandler(new LenientErrorHandler()); + parser.parseResource(Bundle.class, string); + } + + /** + * Test for the url generated based on the server config + */ + @Test + public void testCustomUrlExtension() { + final String expected = ""; + + final MyPatientWithCustomUrlExtension patient = new MyPatientWithCustomUrlExtension(); + patient.setPetName(new StringType("myName")); + + final IParser xmlParser = ourCtx.newXmlParser(); + xmlParser.setServerBaseUrl("http://www.example.com"); + + final String parsedPatient = xmlParser.encodeResourceToString(patient); + System.out.println(parsedPatient); + assertEquals(expected, parsedPatient); + + // Parse with string + MyPatientWithCustomUrlExtension newPatient = xmlParser.parseResource(MyPatientWithCustomUrlExtension.class, parsedPatient); + assertEquals("myName", newPatient.getPetName().getValue()); + + // Parse with stream + newPatient = xmlParser.parseResource(MyPatientWithCustomUrlExtension.class, new StringReader(parsedPatient)); + assertEquals("myName", newPatient.getPetName().getValue()); + + // Check no NPE if base server not configure + newPatient = ourCtx.newXmlParser().parseResource(MyPatientWithCustomUrlExtension.class, new StringReader(parsedPatient)); + assertNull("myName", newPatient.getPetName().getValue()); + assertEquals("myName", ((StringType) newPatient.getExtensionsByUrl("http://www.example.com/petname").get(0).getValue()).getValue()); + } + + @Test + public void testCustomUrlExtensioninBundle() { + final String expected = ""; + + final MyPatientWithCustomUrlExtension patient = new MyPatientWithCustomUrlExtension(); + patient.setPetName(new StringType("myName")); + + final Bundle bundle = new Bundle(); + final BundleEntryComponent entry = new BundleEntryComponent(); + entry.setResource(patient); + bundle.addEntry(entry); + + final IParser xmlParser = ourCtx.newXmlParser(); + xmlParser.setServerBaseUrl("http://www.example.com"); + + final String parsedBundle = xmlParser.encodeResourceToString(bundle); + System.out.println(parsedBundle); + assertEquals(expected, parsedBundle); + + // Parse with string + Bundle newBundle = xmlParser.parseResource(Bundle.class, parsedBundle); + assertNotNull(newBundle); + assertEquals(1, newBundle.getEntry().size()); + Patient newPatient = (Patient) newBundle.getEntry().get(0).getResource(); + assertEquals("myName", ((StringType) newPatient.getExtensionsByUrl("http://www.example.com/petname").get(0).getValue()).getValue()); + + // Parse with stream + newBundle = xmlParser.parseResource(Bundle.class, new StringReader(parsedBundle)); + assertNotNull(newBundle); + assertEquals(1, newBundle.getEntry().size()); + newPatient = (Patient) newBundle.getEntry().get(0).getResource(); + assertEquals("myName", ((StringType) newPatient.getExtensionsByUrl("http://www.example.com/petname").get(0).getValue()).getValue()); + + } + + @Test + public void testDuration() { + Encounter enc = new Encounter(); + Duration duration = new Duration(); + duration.setUnit("day").setValue(123L); + enc.setLength(duration); + + String str = ourCtx.newXmlParser().encodeResourceToString(enc); + ourLog.info(str); + + assertThat(str, not(containsString("meta"))); + assertThat(str, containsString("")); + } + + @Test + public void testEncodeAndParseBundleWithResourceRefs() { + + Patient pt = new Patient(); + pt.setId("patid"); + pt.addName().setFamily("PATIENT"); + + Organization org = new Organization(); + org.setId("orgid"); + org.setName("ORG"); + pt.getManagingOrganization().setResource(org); + + Bundle bundle = new Bundle(); + bundle.addEntry().setResource(pt); + bundle.addEntry().setResource(org); + + String encoded = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(bundle); + ourLog.info(encoded); + + assertThat(encoded, stringContainsInOrder( + "", + "", + "", + "")); + + bundle = ourCtx.newXmlParser().parseResource(Bundle.class, encoded); + pt = (Patient) bundle.getEntry().get(0).getResource(); + org = (Organization) bundle.getEntry().get(1).getResource(); + + assertEquals("Organization/orgid", org.getIdElement().getValue()); + assertEquals("Organization/orgid", pt.getManagingOrganization().getReferenceElement().getValue()); + assertSame(org, pt.getManagingOrganization().getResource()); + } + + @Test + public void testEncodeAndParseCompositeExtension() { + PatientWithCustomCompositeExtension pat = new PatientWithCustomCompositeExtension(); + pat.setId("123"); + pat.setFooParentExtension(new FooParentExtension()); + pat.getFooParentExtension().setChildA(new StringType("ValueA")); + pat.getFooParentExtension().setChildB(new StringType("ValueB")); + + String enc = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(pat); + ourLog.info(enc); + + pat = ourCtx.newXmlParser().parseResource(PatientWithCustomCompositeExtension.class, enc); + + assertEquals("ValueA", pat.getFooParentExtension().getChildA().getValue()); + assertEquals("ValueB", pat.getFooParentExtension().getChildB().getValue()); + } + + @Test + public void testEncodeAndParseContained() { + IParser xmlParser = ourCtx.newXmlParser().setPrettyPrint(true); + + // Create an organization, note that the organization does not have an ID + Organization org = new Organization(); + org.getNameElement().setValue("Contained Test Organization"); + + // Create a patient + Patient patient = new Patient(); + patient.setId("Patient/1333"); + patient.addIdentifier().setSystem("urn:mrns").setValue("253345"); + + // Put the organization as a reference in the patient resource + patient.getManagingOrganization().setResource(org); + + String encoded = xmlParser.encodeResourceToString(patient); + ourLog.info(encoded); + assertThat(encoded, containsString("")); + assertThat(encoded, containsString("")); + + // Create a bundle with just the patient resource + Bundle b = new Bundle(); + b.addEntry().setResource(patient); + + // Encode the bundle + encoded = xmlParser.encodeResourceToString(b); + ourLog.info(encoded); + assertThat(encoded, stringContainsInOrder(Arrays.asList("", "", ""))); + assertThat(encoded, containsString("")); + assertThat(encoded, stringContainsInOrder(Arrays.asList("", ""))); + assertThat(encoded, not(stringContainsInOrder(Arrays.asList("", "", "")))); + + // Re-parse the bundle + patient = (Patient) xmlParser.parseResource(xmlParser.encodeResourceToString(patient)); + assertEquals("#1", patient.getManagingOrganization().getReference()); + + assertNotNull(patient.getManagingOrganization().getResource()); + org = (Organization) patient.getManagingOrganization().getResource(); + assertEquals("#1", org.getIdElement().getValue()); + assertEquals("Contained Test Organization", org.getName()); + + // And re-encode a second time + encoded = xmlParser.encodeResourceToString(patient); + ourLog.info(encoded); + assertThat(encoded, stringContainsInOrder(Arrays.asList("", "", "", ""))); + assertThat(encoded, not(stringContainsInOrder(Arrays.asList("", "")))); + assertThat(encoded, containsString("")); + + // And re-encode once more, with the references cleared + patient.getContained().clear(); + patient.getManagingOrganization().setReference((String) null); + encoded = xmlParser.encodeResourceToString(patient); + ourLog.info(encoded); + assertThat(encoded, stringContainsInOrder(Arrays.asList("", "", "", ""))); + assertThat(encoded, not(stringContainsInOrder(Arrays.asList("", "")))); + assertThat(encoded, containsString("")); + + // And re-encode once more, with the references cleared and a manually set local ID + patient.getContained().clear(); + patient.getManagingOrganization().setReference((String) null); + patient.getManagingOrganization().getResource().setId(("#333")); + encoded = xmlParser.encodeResourceToString(patient); + ourLog.info(encoded); + assertThat(encoded, stringContainsInOrder(Arrays.asList("", "", "", ""))); + assertThat(encoded, not(stringContainsInOrder(Arrays.asList("", "")))); + + } + + @Test + public void testEncodeAndParseContainedCustomTypes() { + ourCtx = FhirContext.forDstu3(); + ourCtx.setDefaultTypeForProfile(CustomObservation.PROFILE, CustomObservation.class); + ourCtx.setDefaultTypeForProfile(CustomDiagnosticReport.PROFILE, CustomDiagnosticReport.class); + + CustomObservation obs = new CustomObservation(); + obs.setStatus(ObservationStatus.FINAL); + + CustomDiagnosticReport dr = new CustomDiagnosticReport(); + dr.setStatus(DiagnosticReportStatus.FINAL); + dr.addResult().setResource(obs); + + IParser parser = ourCtx.newXmlParser(); + parser.setPrettyPrint(true); + + String output = parser.encodeResourceToString(dr); + ourLog.info(output); + + assertThat(output, stringContainsInOrder( + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "")); + + /* + * Now PARSE! + */ + + dr = (CustomDiagnosticReport) parser.parseResource(output); + assertEquals(DiagnosticReportStatus.FINAL, dr.getStatus()); + + assertEquals("#1", dr.getResult().get(0).getReference()); + obs = (CustomObservation) dr.getResult().get(0).getResource(); + assertEquals(ObservationStatus.FINAL, obs.getStatus()); + + ourCtx = null; + } + + @Test + public void testEncodeAndParseContainedNonCustomTypes() { + ourCtx = FhirContext.forDstu3(); + + Observation obs = new Observation(); + obs.setStatus(ObservationStatus.FINAL); + + DiagnosticReport dr = new DiagnosticReport(); + dr.setStatus(DiagnosticReportStatus.FINAL); + dr.addResult().setResource(obs); + + IParser parser = ourCtx.newXmlParser(); + parser.setPrettyPrint(true); + + String output = parser.encodeResourceToString(dr); + ourLog.info(output); + + assertThat(output, stringContainsInOrder( + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "")); + + /* + * Now PARSE! + */ + + dr = (DiagnosticReport) parser.parseResource(output); + assertEquals(DiagnosticReportStatus.FINAL, dr.getStatus()); + + assertEquals("#1", dr.getResult().get(0).getReference()); + obs = (Observation) dr.getResult().get(0).getResource(); + assertEquals(ObservationStatus.FINAL, obs.getStatus()); + + ourCtx = null; + } + + @Test + public void testEncodeAndParseExtensionOnCode() { + Organization o = new Organization(); + o.setName("ORG"); + o.addExtension(new Extension("urn:foo", new CodeType("acode"))); + + String str = ourCtx.newXmlParser().encodeResourceToString(o); + ourLog.info(str); + assertThat(str, containsString("")); + + o = ourCtx.newXmlParser().parseResource(Organization.class, str); + + List exts = o.getExtensionsByUrl("urn:foo"); + assertEquals(1, exts.size()); + CodeType code = (CodeType) exts.get(0).getValue(); + assertEquals("acode", code.getValue()); + + } + + @Test + public void testEncodeAndParseExtensionOnReference() { + DataElement de = new DataElement(); + ElementDefinitionBindingComponent b = de.addElement().getBinding(); + b.setDescription("BINDING"); + + Organization o = new Organization(); + o.setName("ORG"); + b.addExtension(new Extension("urn:foo", new Reference(o))); + + String str = ourCtx.newXmlParser().encodeResourceToString(de); + ourLog.info(str); + + de = ourCtx.newXmlParser().parseResource(DataElement.class, str); + b = de.getElement().get(0).getBinding(); + assertEquals("BINDING", b.getDescription()); + + List exts = b.getExtensionsByUrl("urn:foo"); + assertEquals(1, exts.size()); + Reference rr = (Reference) exts.get(0).getValue(); + o = (Organization) rr.getResource(); + assertEquals("ORG", o.getName()); + + } + + @Test + public void testEncodeAndParseExtensions() throws Exception { + + Patient patient = new Patient(); + patient.addIdentifier().setUse(IdentifierUse.OFFICIAL).setSystem("urn:example").setValue("7000135"); + + Extension ext = new Extension(); + ext.setUrl("http://example.com/extensions#someext"); + ext.setValue(new DateTimeType("2011-01-02T11:13:15")); + patient.addExtension(ext); + + Extension parent = new Extension().setUrl("http://example.com#parent"); + patient.addExtension(parent); + Extension child1 = new Extension().setUrl("http://example.com#child").setValue(new StringType("value1")); + parent.addExtension(child1); + Extension child2 = new Extension().setUrl("http://example.com#child").setValue(new StringType("value2")); + parent.addExtension(child2); + + Extension modExt = new Extension(); + modExt.setUrl("http://example.com/extensions#modext"); + modExt.setValue(new DateType("1995-01-02")); + patient.addModifierExtension(modExt); + + HumanName name = patient.addName(); + name.setFamily("Blah"); + StringType given = name.addGivenElement(); + given.setValue("Joe"); + Extension ext2 = new Extension().setUrl("http://examples.com#givenext").setValue(new StringType("given")); + given.addExtension(ext2); + + StringType given2 = name.addGivenElement(); + given2.setValue("Shmoe"); + Extension given2ext = new Extension().setUrl("http://examples.com#givenext_parent"); + given2.addExtension(given2ext); + given2ext.addExtension(new Extension().setUrl("http://examples.com#givenext_child").setValue(new StringType("CHILD"))); + + String output = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(patient); + ourLog.info(output); + + String enc = ourCtx.newXmlParser().encodeResourceToString(patient); + assertThat(enc, containsString("")); + assertThat(enc, containsString("")); + assertThat(enc, containsString( + "")); + assertThat(enc, containsString("")); + assertThat(enc, containsString( + "")); + + /* + * Now parse this back + */ + + Patient parsed = ourCtx.newXmlParser().parseResource(Patient.class, enc); + ext = parsed.getExtension().get(0); + assertEquals("http://example.com/extensions#someext", ext.getUrl()); + assertEquals("2011-01-02T11:13:15", ((DateTimeType) ext.getValue()).getValueAsString()); + + parent = patient.getExtension().get(1); + assertEquals("http://example.com#parent", parent.getUrl()); + assertNull(parent.getValue()); + child1 = parent.getExtension().get(0); + assertEquals("http://example.com#child", child1.getUrl()); + assertEquals("value1", ((StringType) child1.getValue()).getValueAsString()); + child2 = parent.getExtension().get(1); + assertEquals("http://example.com#child", child2.getUrl()); + assertEquals("value2", ((StringType) child2.getValue()).getValueAsString()); + + modExt = parsed.getModifierExtension().get(0); + assertEquals("http://example.com/extensions#modext", modExt.getUrl()); + assertEquals("1995-01-02", ((DateType) modExt.getValue()).getValueAsString()); + + name = parsed.getName().get(0); + + ext2 = name.getGiven().get(0).getExtension().get(0); + assertEquals("http://examples.com#givenext", ext2.getUrl()); + assertEquals("given", ((StringType) ext2.getValue()).getValueAsString()); + + given2ext = name.getGiven().get(1).getExtension().get(0); + assertEquals("http://examples.com#givenext_parent", given2ext.getUrl()); + assertNull(given2ext.getValue()); + Extension given2ext2 = given2ext.getExtension().get(0); + assertEquals("http://examples.com#givenext_child", given2ext2.getUrl()); + assertEquals("CHILD", ((StringType) given2ext2.getValue()).getValue()); + + } + + /** + * See #216 + */ + @Test + public void testEncodeAndParseIdentifierDstu2() { + IParser xmlParser = ourCtx.newXmlParser().setPrettyPrint(true); + + Patient patient = new Patient(); + patient.addIdentifier().setSystem("SYS").setValue("VAL").setType(new CodeableConcept().addCoding(new Coding().setSystem("http://hl7.org/fhir/v2/0203").setCode("MR"))); + + String out = xmlParser.encodeResourceToString(patient); + ourLog.info(out); + + assertThat(out, stringContainsInOrder("", + "", + "", + "", + "", + "", + "", + "", + "", + "")); + + patient = ourCtx.newXmlParser().parseResource(Patient.class, out); + assertEquals("http://hl7.org/fhir/v2/0203", patient.getIdentifier().get(0).getType().getCoding().get(0).getSystem()); + assertEquals("MR", patient.getIdentifier().get(0).getType().getCoding().get(0).getCode()); + } + + /** + * See #347 + */ + @Test + public void testEncodeAndParseMedicationRequest() { + MedicationRequest mo = new MedicationRequest(); + mo.getAuthoredOnElement().setValueAsString("2015-10-05"); + + String encoded = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(mo); + ourLog.info(encoded); + + mo = ourCtx.newXmlParser().parseResource(MedicationRequest.class, encoded); + assertEquals("2015-10-05", mo.getAuthoredOnElement().getValueAsString()); + } + + @Test + public void testEncodeAndParseMetaProfileAndTags() { + Patient p = new Patient(); + p.addName().setFamily("FAMILY"); + + p.getMeta().addProfile("http://foo/Profile1"); + p.getMeta().addProfile("http://foo/Profile2"); + + p.getMeta().addTag().setSystem("scheme1").setCode("term1").setDisplay("label1"); + p.getMeta().addTag().setSystem("scheme2").setCode("term2").setDisplay("label2"); + + p.getMeta().addSecurity().setSystem("sec_scheme1").setCode("sec_term1").setDisplay("sec_label1"); + p.getMeta().addSecurity().setSystem("sec_scheme2").setCode("sec_term2").setDisplay("sec_label2"); + + String enc = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(p); + ourLog.info(enc); + + assertThat(enc, stringContainsInOrder("", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "")); + + Patient parsed = ourCtx.newXmlParser().parseResource(Patient.class, enc); + List gotLabels = parsed.getMeta().getProfile(); + assertEquals(2, gotLabels.size()); + UriType label = gotLabels.get(0); + assertEquals("http://foo/Profile1", label.getValue()); + label = gotLabels.get(1); + assertEquals("http://foo/Profile2", label.getValue()); + + List tagList = parsed.getMeta().getTag(); + assertEquals(2, tagList.size()); + assertEquals("scheme1", tagList.get(0).getSystem()); + assertEquals("term1", tagList.get(0).getCode()); + assertEquals("label1", tagList.get(0).getDisplay()); + assertEquals("scheme2", tagList.get(1).getSystem()); + assertEquals("term2", tagList.get(1).getCode()); + assertEquals("label2", tagList.get(1).getDisplay()); + + tagList = parsed.getMeta().getSecurity(); + assertEquals(2, tagList.size()); + assertEquals("sec_scheme1", tagList.get(0).getSystem()); + assertEquals("sec_term1", tagList.get(0).getCode()); + assertEquals("sec_label1", tagList.get(0).getDisplay()); + assertEquals("sec_scheme2", tagList.get(1).getSystem()); + assertEquals("sec_term2", tagList.get(1).getCode()); + assertEquals("sec_label2", tagList.get(1).getDisplay()); + } + + @Test + public void testEncodeAndParseMetaProfiles() { + Patient p = new Patient(); + p.addName().setFamily("FAMILY"); + + p.getMeta().addTag().setSystem("scheme1").setCode("term1").setDisplay("label1"); + p.getMeta().addTag().setSystem("scheme2").setCode("term2").setDisplay("label2"); + + String enc = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(p); + ourLog.info(enc); + + assertThat(enc, stringContainsInOrder("", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "")); + + Patient parsed = ourCtx.newXmlParser().parseResource(Patient.class, enc); + assertThat(parsed.getMeta().getProfile(), empty()); + + List tagList = parsed.getMeta().getTag(); + assertEquals(2, tagList.size()); + assertEquals("scheme1", tagList.get(0).getSystem()); + assertEquals("term1", tagList.get(0).getCode()); + assertEquals("label1", tagList.get(0).getDisplay()); + assertEquals("scheme2", tagList.get(1).getSystem()); + assertEquals("term2", tagList.get(1).getCode()); + assertEquals("label2", tagList.get(1).getDisplay()); + } + + /** + * See #336 + */ + @Test + public void testEncodeAndParseNullPrimitiveWithExtensions() { + + Patient p = new Patient(); + p.setId("patid"); + HumanName name = p.addName(); + name.addGivenElement().setValue(null).setId("f0").addExtension(new Extension("http://foo", new StringType("FOOEXT0"))); + name.addGivenElement().setValue("V1").setId("f1").addExtension((Extension) new Extension("http://foo", new StringType("FOOEXT1")).setId("ext1id")); + name.addGivenElement(); // this one shouldn't get encoded + name.addGivenElement().setValue(null).addExtension(new Extension("http://foo", new StringType("FOOEXT3"))); + name.setId("nameid"); + + String output = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(p); + ourLog.info(output); + + output = ourCtx.newXmlParser().setPrettyPrint(false).encodeResourceToString(p); + String expected = ""; + + ourLog.info("Expected: {}", expected); + ourLog.info("Actual : {}", output); + + assertEquals(expected, output); + + p = ourCtx.newXmlParser().parseResource(Patient.class, output); + assertEquals("patid", p.getIdElement().getIdPart()); + + name = p.getName().get(0); + assertEquals("nameid", name.getId()); + assertEquals(3, name.getGiven().size()); + + assertEquals(null, name.getGiven().get(0).getValue()); + assertEquals("V1", name.getGiven().get(1).getValue()); + assertEquals(null, name.getGiven().get(2).getValue()); + + assertEquals("f0", name.getGiven().get(0).getId()); + assertEquals("f1", name.getGiven().get(1).getId()); + assertEquals(null, name.getGiven().get(2).getId()); + + assertEquals(1, name.getGiven().get(0).getExtension().size()); + assertEquals("http://foo", name.getGiven().get(0).getExtension().get(0).getUrl()); + assertEquals("FOOEXT0", ((StringType) name.getGiven().get(0).getExtension().get(0).getValue()).getValue()); + assertEquals(null, name.getGiven().get(0).getExtension().get(0).getId()); + + assertEquals(1, name.getGiven().get(1).getExtension().size()); + assertEquals("http://foo", name.getGiven().get(1).getExtension().get(0).getUrl()); + assertEquals("FOOEXT1", ((StringType) name.getGiven().get(1).getExtension().get(0).getValue()).getValue()); + assertEquals("ext1id", name.getGiven().get(1).getExtension().get(0).getId()); + + assertEquals(1, name.getGiven().get(2).getExtension().size()); + assertEquals("http://foo", name.getGiven().get(2).getExtension().get(0).getUrl()); + assertEquals("FOOEXT3", ((StringType) name.getGiven().get(2).getExtension().get(0).getValue()).getValue()); + assertEquals(null, name.getGiven().get(2).getExtension().get(0).getId()); + + } + + @Test + public void testEncodeAndParseProfiledDatatype() { + MedicationRequest mo = new MedicationRequest(); + mo.addDosageInstruction().getTiming().getRepeat().setBounds(new Duration().setCode("code")); + String out = ourCtx.newXmlParser().encodeResourceToString(mo); + ourLog.info(out); + assertThat(out, containsString("")); + + mo = ourCtx.newXmlParser().parseResource(MedicationRequest.class, out); + Duration duration = (Duration) mo.getDosageInstruction().get(0).getTiming().getRepeat().getBounds(); + assertEquals("code", duration.getCode()); + } + + /** + * See #216 - Profiled datatypes should use their unprofiled parent type as the choice[x] name + */ + @Test + public void testEncodeAndParseProfiledDatatypeChoice() throws Exception { + IParser xmlParser = ourCtx.newXmlParser(); + + MedicationStatement ms = new MedicationStatement(); + ms.addDosage().setDose(new SimpleQuantity().setValue(123)); + + String output = xmlParser.encodeResourceToString(ms); + assertThat(output, containsString("")); + } + + @Test + public void testEncodeAndParseSecurityLabels() { + Patient p = new Patient(); + p.addName().setFamily("FAMILY"); + + List labels = new ArrayList(); + labels.add(new Coding().setSystem("SYSTEM1").setCode("CODE1").setDisplay("DISPLAY1").setVersion("VERSION1")); + labels.add(new Coding().setSystem("SYSTEM2").setCode("CODE2").setDisplay("DISPLAY2").setVersion("VERSION2")); + p.getMeta().getSecurity().addAll(labels); + + String enc = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(p); + ourLog.info(enc); + + assertThat(enc, stringContainsInOrder("", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "")); + + Patient parsed = ourCtx.newXmlParser().parseResource(Patient.class, enc); + List gotLabels = parsed.getMeta().getSecurity(); + + assertEquals(2, gotLabels.size()); + + Coding label = gotLabels.get(0); + assertEquals("SYSTEM1", label.getSystem()); + assertEquals("CODE1", label.getCode()); + assertEquals("DISPLAY1", label.getDisplay()); + assertEquals("VERSION1", label.getVersion()); + + label = gotLabels.get(1); + assertEquals("SYSTEM2", label.getSystem()); + assertEquals("CODE2", label.getCode()); + assertEquals("DISPLAY2", label.getDisplay()); + assertEquals("VERSION2", label.getVersion()); + } + + /** + * See #103 + */ + @Test + public void testEncodeAndReEncodeContainedJson() { + Composition comp = new Composition(); + comp.addSection().addEntry().setResource(new AllergyIntolerance().addNote(new Annotation().setText("Section0_Allergy0"))); + comp.addSection().addEntry().setResource(new AllergyIntolerance().addNote(new Annotation().setText("Section1_Allergy0"))); + comp.addSection().addEntry().setResource(new AllergyIntolerance().addNote(new Annotation().setText("Section2_Allergy0"))); + + IParser parser = ourCtx.newJsonParser().setPrettyPrint(true); + + String string = parser.encodeResourceToString(comp); + ourLog.info(string); + + Composition parsed = parser.parseResource(Composition.class, string); + parsed.getSection().remove(0); + + string = parser.encodeResourceToString(parsed); + ourLog.info(string); + + parsed = parser.parseResource(Composition.class, string); + assertEquals(2, parsed.getContained().size()); + } + + /** + * See #103 + */ + @Test + public void testEncodeAndReEncodeContainedXml() { + Composition comp = new Composition(); + comp.addSection().addEntry().setResource(new AllergyIntolerance().addNote(new Annotation().setText("Section0_Allergy0"))); + comp.addSection().addEntry().setResource(new AllergyIntolerance().addNote(new Annotation().setText("Section1_Allergy0"))); + comp.addSection().addEntry().setResource(new AllergyIntolerance().addNote(new Annotation().setText("Section2_Allergy0"))); + + IParser parser = ourCtx.newXmlParser().setPrettyPrint(true); + + String string = parser.encodeResourceToString(comp); + ourLog.info(string); + + Composition parsed = parser.parseResource(Composition.class, string); + parsed.getSection().remove(0); + + string = parser.encodeResourceToString(parsed); + ourLog.info(string); + + parsed = parser.parseResource(Composition.class, string); + assertEquals(2, parsed.getContained().size()); + } + + @Test + public void testEncodeBinaryWithNoContentType() { + Binary b = new Binary(); + b.setContent(new byte[] { 1, 2, 3, 4 }); + + String output = ourCtx.newXmlParser().encodeResourceToString(b); + ourLog.info(output); + + assertEquals("", output); + } + + @Test + public void testEncodeBundleWithContained() { + DiagnosticReport rpt = new DiagnosticReport(); + rpt.addResult().setResource(new Observation().setCode(new CodeableConcept().setText("Sharp1")).setId("#1")); + rpt.addResult().setResource(new Observation().setCode(new CodeableConcept().setText("Uuid1")).setId("urn:uuid:UUID1")); + + Bundle b = new Bundle(); + b.addEntry().setResource(rpt); + + String encoded = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(b); + ourLog.info(encoded); + + assertThat(encoded, stringContainsInOrder("", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "")); + + } + + /** + * See #113 + */ + @Test + public void testEncodeContainedResources() { + + MedicationRequest medicationPrescript = new MedicationRequest(); + + String medId = "123"; + CodeableConcept codeDt = new CodeableConcept().addCoding(new Coding().setSystem("urn:sys").setCode("code1")); + + // Adding medication to Contained. + Medication medResource = new Medication(); + medResource.setCode(codeDt); + medResource.setId("#" + String.valueOf(medId)); + medicationPrescript.getContained().add(medResource); + + // Medication reference. This should point to the contained resource. + Reference medRefDt = new Reference("#" + medId); + medRefDt.setDisplay("MedRef"); + medicationPrescript.setMedication(medRefDt); + + IParser p = ourCtx.newXmlParser().setPrettyPrint(true); + String encoded = p.encodeResourceToString(medicationPrescript); + ourLog.info(encoded); + + // @formatter:on + assertThat(encoded, + stringContainsInOrder("", "", "", "", "", "", + "", "", "", "", "", "", "", "", + "", "", "")); + + } + + /** + * See #113 + */ + @Test + public void testEncodeContainedResourcesAutomatic() { + + MedicationRequest medicationPrescript = new MedicationRequest(); + String nameDisp = "MedRef"; + CodeableConcept codeDt = new CodeableConcept().addCoding(new Coding("urn:sys", "code1", null)); + + // Adding medication to Contained. + Medication medResource = new Medication(); + // No ID set + medResource.setCode(codeDt); + + // Medication reference. This should point to the contained resource. + Reference medRefDt = new Reference(); + medRefDt.setDisplay(nameDisp); + // Resource reference set, but no ID + medRefDt.setResource(medResource); + medicationPrescript.setMedication(medRefDt); + + IParser p = ourCtx.newXmlParser().setPrettyPrint(true); + String encoded = p.encodeResourceToString(medicationPrescript); + ourLog.info(encoded); + + assertThat(encoded, + stringContainsInOrder("", "", "", "", "", "", + "", "", "", "", "", "", "", "", + "", "", "")); + + } + + /** + * See #113 + */ + @Test + public void testEncodeContainedResourcesManualContainUsingNonLocalId() { + + MedicationRequest medicationPrescript = new MedicationRequest(); + + String medId = "123"; + CodeableConcept codeDt = new CodeableConcept().addCoding(new Coding("urn:sys", "code1", null)); + + // Adding medication to Contained. + Medication medResource = new Medication(); + medResource.setCode(codeDt); + medResource.setId(String.valueOf(medId)); // ID does not start with '#' + medicationPrescript.getContained().add(medResource); + + // Medication reference. This should point to the contained resource. + Reference medRefDt = new Reference("#" + medId); + medRefDt.setDisplay("MedRef"); + medicationPrescript.setMedication(medRefDt); + + IParser p = ourCtx.newXmlParser().setPrettyPrint(true); + String encoded = p.encodeResourceToString(medicationPrescript); + ourLog.info(encoded); + + assertThat(encoded, + stringContainsInOrder("", "", "", "", "", "", + "", "", "", "", "", "", "", "", + "", "", "")); + + } + + @Test + public void testEncodeContainedWithNarrativeIsSuppresed() throws Exception { + IParser parser = ourCtx.newXmlParser().setPrettyPrint(true); + + // Create an organization, note that the organization does not have an ID + Organization org = new Organization(); + org.getNameElement().setValue("Contained Test Organization"); + org.getText().setDivAsString("
FOOBAR
"); + + // Create a patient + Patient patient = new Patient(); + patient.setId("Patient/1333"); + patient.addIdentifier().setSystem("urn:mrns").setValue("253345"); + patient.getText().setDivAsString("
BARFOO
"); + patient.getManagingOrganization().setResource(org); + + String encoded = parser.encodeResourceToString(patient); + ourLog.info(encoded); + + assertThat(encoded, stringContainsInOrder("", "
BARFOO
", "", "", "", "")); + assertThat(encode, stringContainsInOrder("\n\n

A P TAG

line1\nline2\nline3  BOLD

"); + + String output = ourCtx.newXmlParser().setPrettyPrint(false).encodeResourceToString(p); + ourLog.info(output); + + assertThat(output, stringContainsInOrder( + "A P TAG

", + "

line1\nline2\nline3  BOLD
")); + + } + + @Test + public void testEncodeDivWithPrePrettyPrint() { + + Patient p = new Patient(); + p.getText().setDivAsString("
\n\n

A P TAG

line1\nline2\nline3  BOLD

"); + + String output = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(p); + ourLog.info(output); + + assertThat(output, stringContainsInOrder( + " ", + " line1\nline2\nline3 BOLD")); + + } + + @Test + public void testEncodeDoesntIncludeUuidId() { + Patient p = new Patient(); + p.setId(new IdType("urn:uuid:42795ed8-041f-4ebf-b6f4-78ef6f64c2f2")); + p.addIdentifier().setSystem("ACME"); + + String actual = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(p); + assertThat(actual, not(containsString("78ef6f64c2f2"))); + } + + @Test + public void testEncodeEmptyBinary() { + String output = ourCtx.newXmlParser().encodeResourceToString(new Binary()); + assertEquals("", output); + } + + /** + * #158 + */ + @Test + public void testEncodeEmptyTag() { + ArrayList tagList = new ArrayList(); + tagList.add(new Coding()); + tagList.add(new Coding().setDisplay("Label")); + + Patient p = new Patient(); + p.getMeta().getTag().addAll(tagList); + + String encoded = ourCtx.newXmlParser().encodeResourceToString(p); + assertThat(encoded, not(containsString("tag"))); + } + + /** + * #158 + */ + @Test + public void testEncodeEmptyTag2() { + ArrayList tagList = new ArrayList(); + tagList.add(new Coding().setSystem("scheme").setCode("code")); + tagList.add(new Coding().setDisplay("Label")); + + Patient p = new Patient(); + p.getMeta().getTag().addAll(tagList); + + String encoded = ourCtx.newXmlParser().encodeResourceToString(p); + assertThat(encoded, containsString("tag")); + assertThat(encoded, containsString("scheme")); + assertThat(encoded, not(containsString("Label"))); + } + + @Test + public void testEncodeExtensionOnRoot() { + Patient p = new Patient(); + p.setId("Patient/B"); + p + .addExtension() + .setUrl("http://foo") + .setValue(new Reference("Practitioner/A")); + IParser parser = ourCtx.newXmlParser().setPrettyPrint(true); + parser.setDontEncodeElements(new HashSet(Arrays.asList("*.id", "*.meta"))); + + String encoded = parser.encodeResourceToString(p); + ourLog.info(encoded); + + assertThat(encoded, containsString("http://foo")); + assertThat(encoded, containsString("Practitioner/A")); + } + + @Test + public void testEncodeExtensionUndeclaredNonModifier() { + Observation obs = new Observation(); + obs.setId("1"); + obs.getMeta().addProfile("http://profile"); + Extension ext = obs.addExtension(); + ext.setUrl("http://exturl").setValue(new StringType("ext_url_value")); + + obs.getCode().setText("CODE"); + + IParser parser = ourCtx.newXmlParser(); + + String output = parser.setPrettyPrint(true).encodeResourceToString(obs); + ourLog.info(output); + + assertThat(output, stringContainsInOrder( + "", + "", + "", + "", + "", + "")); + assertThat(output, not(stringContainsInOrder( + ""))); + + obs = parser.parseResource(Observation.class, output); + assertEquals(1, obs.getExtension().size()); + assertEquals("http://exturl", obs.getExtension().get(0).getUrl()); + assertEquals("ext_url_value", ((StringType) obs.getExtension().get(0).getValue()).getValue()); + } + + @Test + public void testEncodeExtensionUndeclaredNonModifierWithChildExtension() { + Observation obs = new Observation(); + obs.setId("1"); + obs.getMeta().addProfile("http://profile"); + Extension ext = obs.addExtension(); + ext.setUrl("http://exturl"); + + Extension subExt = ext.addExtension(); + subExt.setUrl("http://subext").setValue(new StringType("sub_ext_value")); + + obs.getCode().setText("CODE"); + + IParser parser = ourCtx.newXmlParser(); + + String output = parser.setPrettyPrint(true).encodeResourceToString(obs); + ourLog.info(output); + + assertThat(output, stringContainsInOrder( + "", + "", + "", + "", + "", + "", + "")); + assertThat(output, not(stringContainsInOrder( + ""))); + + obs = parser.parseResource(Observation.class, output); + assertEquals(1, obs.getExtension().size()); + assertEquals("http://exturl", obs.getExtension().get(0).getUrl()); + assertEquals(1, obs.getExtension().get(0).getExtension().size()); + assertEquals("http://subext", obs.getExtension().get(0).getExtension().get(0).getUrl()); + assertEquals("sub_ext_value", ((StringType) obs.getExtension().get(0).getExtension().get(0).getValue()).getValue()); + } + + /** + * See #327 + */ + @Test + public void testEncodeExtensionWithContainedResource() { + + TestPatientFor327 patient = new TestPatientFor327(); + patient.setBirthDateElement(new DateType("2016-04-14")); + + List conditions = new ArrayList(); + Condition condition = new Condition(); + condition.addBodySite().setText("BODY SITE"); + conditions.add(new Reference(condition)); + patient.setCondition(conditions); + + String encoded = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(patient); + ourLog.info(encoded); + + assertThat(encoded, stringContainsInOrder( + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "")); + + } + + @Test + public void testEncodeExtensionWithResourceContent() { + IParser parser = ourCtx.newXmlParser(); + + Patient patient = new Patient(); + patient.addAddress().setUse(AddressUse.HOME); + patient.addExtension(new Extension("urn:foo", new Reference("Organization/123"))); + + String val = parser.encodeResourceToString(patient); + ourLog.info(val); + assertThat(val, StringContains.containsString("")); + + Patient actual = parser.parseResource(Patient.class, val); + assertEquals(AddressUse.HOME, patient.getAddress().get(0).getUse()); + List ext = actual.getExtension(); + assertEquals(1, ext.size()); + Reference ref = (Reference) ext.get(0).getValue(); + assertEquals("Organization/123", ref.getReference()); + + } + + @Test + public void testEncodeHistoryEncodeVersionsAtPath3() { + ourCtx = FhirContext.forDstu3(); + + assertNull(ourCtx.newXmlParser().getStripVersionsFromReferences()); + + AuditEvent auditEvent = new AuditEvent(); + auditEvent.addEntity().setReference(new Reference("http://foo.com/Organization/2/_history/1")); + + IParser parser = ourCtx.newXmlParser(); + + parser.setDontStripVersionsFromReferencesAtPaths("AuditEvent.entity.reference"); + String enc = parser.setPrettyPrint(true).encodeResourceToString(auditEvent); + ourLog.info(enc); + assertThat(enc, containsString("")); + + parser.setDontStripVersionsFromReferencesAtPaths(new ArrayList()); + enc = parser.setPrettyPrint(true).encodeResourceToString(auditEvent); + ourLog.info(enc); + assertThat(enc, containsString("")); + + parser.setDontStripVersionsFromReferencesAtPaths((String[]) null); + enc = parser.setPrettyPrint(true).encodeResourceToString(auditEvent); + ourLog.info(enc); + assertThat(enc, containsString("")); + + parser.setDontStripVersionsFromReferencesAtPaths((List) null); + enc = parser.setPrettyPrint(true).encodeResourceToString(auditEvent); + ourLog.info(enc); + assertThat(enc, containsString("")); + + } + + @Test + public void testEncodeNarrativeSuppressed() { + Patient patient = new Patient(); + patient.setId("Patient/1/_history/1"); + patient.getText().setDivAsString("
THE DIV
"); + patient.addName().setFamily("FAMILY"); + patient.setMaritalStatus(new CodeableConcept().addCoding(new Coding().setCode("D"))); + patient.setMaritalStatus(new CodeableConcept().addCoding(new Coding().setCode("D"))); + + String encoded = ourCtx.newXmlParser().setPrettyPrint(true).setSuppressNarratives(true).encodeResourceToString(patient); + ourLog.info(encoded); + + assertThat(encoded, containsString("", "", "", "")); + assertThat(encoded, not(containsString("text"))); + assertThat(encoded, not(containsString("THE DIV"))); + assertThat(encoded, containsString("family")); + assertThat(encoded, containsString("maritalStatus")); + } + + @Test + public void testEncodeNonContained() { + // Create an organization + Organization org = new Organization(); + org.setId("Organization/65546"); + org.getNameElement().setValue("Contained Test Organization"); + + // Create a patient + Patient patient = new Patient(); + patient.setId("Patient/1333"); + patient.addIdentifier().setSystem("urn:mrns").setValue("253345"); + patient.getManagingOrganization().setResource(org); + + // Create a list containing both resources. In a server method, you might just + // return this list, but here we will create a bundle to encode. + List resources = new ArrayList(); + resources.add(org); + resources.add(patient); + + // Create a bundle with both + Bundle b = new Bundle(); + b.addEntry().setResource(org); + b.addEntry().setResource(patient); + + // Encode the buntdle + String encoded = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(b); + ourLog.info(encoded); + assertThat(encoded, not(containsString(""))); + assertThat(encoded, stringContainsInOrder("", "
")); + assertThat(encoded, containsString("")); + assertThat(encoded, stringContainsInOrder("", "
")); + + encoded = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(patient); + ourLog.info(encoded); + assertThat(encoded, not(containsString(""))); + assertThat(encoded, containsString("")); + + } + + /** + * See #312 + */ + @Test + public void testEncodeNullElement() { + Patient patient = new Patient(); + patient.addName().getGiven().add(null); + + IParser parser = ourCtx.newXmlParser(); + String xml = parser.encodeResourceToString(patient); + + ourLog.info(xml); + assertEquals("", xml); + } + + /** + * See #312 + */ + @Test + public void testEncodeNullExtension() { + Patient patient = new Patient(); + patient.getExtension().add(null); // Purposely add null + patient.getModifierExtension().add(null); // Purposely add null + patient.getExtension().add(new Extension("http://hello.world", new StringType("Hello World"))); + patient.getName().add(null); + patient.addName().getGiven().add(null); + + IParser parser = ourCtx.newXmlParser(); + String xml = parser.encodeResourceToString(patient); + + ourLog.info(xml); + assertEquals("", xml); + } + + @Test + public void testEncodeReferenceUsingUnqualifiedResourceWorksCorrectly() { + + Patient patient = new Patient(); + patient.setId("phitcc_pat_normal"); + patient.addName().addGiven("Patty").setUse(NameUse.NICKNAME); + patient.addTelecom().setSystem(ContactPointSystem.EMAIL).setValue("patpain@ehealthinnovation.org"); + patient.setGender(AdministrativeGender.FEMALE); + patient.setBirthDateElement(new DateType("2001-10-13")); + + DateTimeType obsEffectiveTime = new DateTimeType("2015-04-11T12:22:01-04:00"); + + Observation obsParent = new Observation(); + obsParent.setId("phitcc_obs_bp_parent"); + obsParent.getSubject().setResource(patient); + obsParent.setStatus(ObservationStatus.FINAL); + obsParent.setEffective(obsEffectiveTime); + + Observation obsSystolic = new Observation(); + obsSystolic.setId("phitcc_obs_bp_dia"); + obsSystolic.getSubject().setResource(patient); + obsSystolic.setEffective(obsEffectiveTime); + obsParent.addRelated().setType(ObservationRelationshipType.HASMEMBER).setTarget(new Reference(obsSystolic)); + + Observation obsDiastolic = new Observation(); + obsDiastolic.setId("phitcc_obs_bp_dia"); + obsDiastolic.getSubject().setResource(patient); + obsDiastolic.setEffective(obsEffectiveTime); + obsParent.addRelated().setType(ObservationRelationshipType.HASMEMBER).setTarget(new Reference(obsDiastolic)); + + String str = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(obsParent); + ourLog.info(str); + + assertThat(str, containsString("")); + assertThat(str, containsString("")); + } + + @Test + public void testEncodeReferenceWithUuid() { + + Practitioner pract = new Practitioner(); + pract.setId(IdType.newRandomUuid()); + pract.addName().setFamily("PRACT FAMILY"); + + Patient patient = new Patient(); + patient.addGeneralPractitioner().setResource(pract); + + String encoded = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(patient); + ourLog.info(encoded); + + assertThat(pract.getId(), startsWith("urn:uuid:")); + assertThat(encoded, containsString("")); + } + + @Test + public void testEncodeSummary() { + Patient patient = new Patient(); + patient.setId("Patient/1/_history/1"); + patient.getText().setDivAsString("
THE DIV
"); + patient.addName().setFamily("FAMILY"); + patient.setMaritalStatus(new CodeableConcept().addCoding(new Coding().setCode("D"))); + + String encoded = ourCtx.newXmlParser().setPrettyPrint(true).setSummaryMode(true).encodeResourceToString(patient); + ourLog.info(encoded); + + assertThat(encoded, containsString("", "", "", "")); + assertThat(encoded, not(containsString("THE DIV"))); + assertThat(encoded, containsString("family")); + assertThat(encoded, not(containsString("maritalStatus"))); + } + + @Test + public void testEncodeSummary2() { + Patient patient = new Patient(); + patient.setId("Patient/1/_history/1"); + patient.getText().setDivAsString("
THE DIV
"); + patient.addName().setFamily("FAMILY"); + patient.setMaritalStatus(new CodeableConcept().addCoding(new Coding().setCode("D"))); + + patient.getMeta().addTag().setSystem("foo").setCode("bar"); + + String encoded = ourCtx.newXmlParser().setPrettyPrint(true).setSummaryMode(true).encodeResourceToString(patient); + ourLog.info(encoded); + + assertThat(encoded, containsString("", "", "", "")); + assertThat(encoded, stringContainsInOrder("", "", "", "")); + assertThat(encoded, not(containsString("THE DIV"))); + assertThat(encoded, containsString("family")); + assertThat(encoded, not(containsString("maritalStatus"))); + } + + @Test + public void testEncodeUndeclaredBlock() throws Exception { + FooMessageHeader.FooMessageSourceComponent source = new FooMessageHeader.FooMessageSourceComponent(); + source.getMessageHeaderApplicationId().setValue("APPID"); + source.setName("NAME"); + + FooMessageHeader header = new FooMessageHeader(); + header.setSource(source); + + header.addDestination().setName("DEST"); + + Bundle bundle = new Bundle(); + bundle.addEntry().setResource(header); + + IParser p = ourCtx.newXmlParser(); + p.setPrettyPrint(true); + + String encode = p.encodeResourceToString(bundle); + ourLog.info(encode); + + assertThat(encode, containsString("")); + assertThat(encode, stringContainsInOrder(" fact = new AddressUseEnumFactory(); + PrimitiveType enumeration = new Enumeration(fact).setValue(AddressUse.HOME); + patient.addExtension().setUrl("urn:foo").setValue(enumeration); + + String val = parser.encodeResourceToString(patient); + ourLog.info(val); + assertThat(val, StringContains.containsString("")); + + MyPatientWithOneDeclaredEnumerationExtensionDstu3 actual = parser.parseResource(MyPatientWithOneDeclaredEnumerationExtensionDstu3.class, val); + assertEquals(AddressUse.HOME, patient.getAddress().get(0).getUse()); + Enumeration ref = actual.getFoo(); + assertEquals("home", ref.getValue().toCode()); + + } + + @Test + public void testEncodeWithContained() { + List contained = new ArrayList(); + + // Will be added by reference + Patient p = new Patient(); + p.setId("#" + "1000"); + contained.add(p); + + // Will be added by direct resource object + Location l = new Location(); + l.setId("#" + "1001"); + contained.add(l); + + // Will not be referred to (and therefore shouldn't appear in output) + Location l2 = new Location(); + l2.setId("#1002"); + contained.add(l2); + + Appointment appointment = new Appointment(); + appointment.setId("1234"); + appointment.getContained().addAll(contained); + + appointment.addParticipant().getActor().setReference("#1000"); + appointment.addParticipant().getActor().setResource(l); + + String encoded = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(appointment); + ourLog.info(encoded); + + assertThat(encoded, stringContainsInOrder( + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "")); + + assertThat(encoded, not(containsString("#1002"))); + } + + @Test + public void testEncodeWithDontEncodeElements() throws Exception { + Patient patient = new Patient(); + patient.setId("123"); + patient.getMeta().addProfile("http://profile"); + patient.addName().setFamily("FAMILY").addGiven("GIVEN"); + patient.addAddress().addLine("LINE1"); + + { + IParser p = ourCtx.newXmlParser(); + p.setDontEncodeElements(Sets.newHashSet("*.meta", "*.id")); + p.setPrettyPrint(true); + String out = p.encodeResourceToString(patient); + ourLog.info(out); + assertThat(out, containsString("Patient")); + assertThat(out, containsString("name")); + assertThat(out, containsString("address")); + assertThat(out, not(containsString("id"))); + assertThat(out, not(containsString("meta"))); + } + { + IParser p = ourCtx.newXmlParser(); + p.setDontEncodeElements(Sets.newHashSet("Patient.meta", "Patient.id")); + p.setPrettyPrint(true); + String out = p.encodeResourceToString(patient); + ourLog.info(out); + assertThat(out, containsString("Patient")); + assertThat(out, containsString("name")); + assertThat(out, containsString("address")); + assertThat(out, not(containsString("id"))); + assertThat(out, not(containsString("meta"))); + } + { + IParser p = ourCtx.newXmlParser(); + p.setDontEncodeElements(Sets.newHashSet("Patient.name.family")); + p.setPrettyPrint(true); + String out = p.encodeResourceToString(patient); + ourLog.info(out); + assertThat(out, containsString("GIVEN")); + assertThat(out, not(containsString("FAMILY"))); + } + { + IParser p = ourCtx.newXmlParser(); + p.setDontEncodeElements(Sets.newHashSet("*.meta", "*.id")); + p.setPrettyPrint(true); + String out = p.encodeResourceToString(patient); + ourLog.info(out); + assertThat(out, containsString("Patient")); + assertThat(out, containsString("name")); + assertThat(out, containsString("address")); + assertThat(out, not(containsString("id"))); + assertThat(out, not(containsString("meta"))); + } + { + IParser p = ourCtx.newXmlParser(); + p.setDontEncodeElements(Sets.newHashSet("Patient.meta")); + p.setEncodeElements(new HashSet(Arrays.asList("Patient.name"))); + p.setPrettyPrint(true); + String out = p.encodeResourceToString(patient); + ourLog.info(out); + assertThat(out, containsString("Patient")); + assertThat(out, containsString("name")); + assertThat(out, containsString("id")); + assertThat(out, not(containsString("address"))); + assertThat(out, not(containsString("meta"))); + } + } + + @Test + public void testEncodeWithEncodeElements() throws Exception { + Patient patient = new Patient(); + patient.getMeta().addProfile("http://profile"); + patient.addName().setFamily("FAMILY"); + patient.addAddress().addLine("LINE1"); + + Bundle bundle = new Bundle(); + bundle.setTotal(100); + bundle.addEntry().setResource(patient); + + { + IParser p = ourCtx.newXmlParser(); + p.setEncodeElements(new HashSet(Arrays.asList("Patient.name", "Bundle.entry"))); + p.setPrettyPrint(true); + String out = p.encodeResourceToString(bundle); + ourLog.info(out); + assertThat(out, not(containsString("total"))); + assertThat(out, (containsString("Patient"))); + assertThat(out, (containsString("name"))); + assertThat(out, not(containsString("address"))); + } + { + IParser p = ourCtx.newXmlParser(); + p.setEncodeElements(new HashSet(Arrays.asList("Patient.name"))); + p.setEncodeElementsAppliesToResourceTypes(new HashSet(Arrays.asList("Patient"))); + p.setPrettyPrint(true); + String out = p.encodeResourceToString(bundle); + ourLog.info(out); + assertThat(out, (containsString("total"))); + assertThat(out, (containsString("Patient"))); + assertThat(out, (containsString("name"))); + assertThat(out, not(containsString("address"))); + } + { + IParser p = ourCtx.newXmlParser(); + p.setEncodeElements(new HashSet(Arrays.asList("Patient"))); + p.setEncodeElementsAppliesToResourceTypes(new HashSet(Arrays.asList("Patient"))); + p.setPrettyPrint(true); + String out = p.encodeResourceToString(bundle); + ourLog.info(out); + assertThat(out, (containsString("total"))); + assertThat(out, (containsString("Patient"))); + assertThat(out, (containsString("name"))); + assertThat(out, (containsString("address"))); + } + + } + + @Test + public void testEncodeWithNarrative() { + Patient p = new Patient(); + p.addName().setFamily("Smith").addGiven("John"); + + ourCtx.setNarrativeGenerator(new DefaultThymeleafNarrativeGenerator()); + + String output = ourCtx.newXmlParser().encodeResourceToString(p); + ourLog.info(output); + + assertThat(output, containsString("
John SMITH ")); + } + + /** + * Test for the url generated based on the server config + */ + @Test + public void testGeneratedUrls() { + final IParser xmlParser = ourCtx.newXmlParser().setPrettyPrint(true); + xmlParser.setServerBaseUrl("http://myserver.com"); + + final CustomPatientDstu3 patient = new CustomPatientDstu3(); + patient.setHomeless(new BooleanType(true)); + + final String parsedPatient = xmlParser.encodeResourceToString(patient); + + assertTrue(parsedPatient.contains("")); + assertTrue(parsedPatient.contains("")); + } + + @Test + public void testMoreExtensions() throws Exception { + + Patient patient = new Patient(); + patient.addIdentifier().setUse(IdentifierUse.OFFICIAL).setSystem("urn:example").setValue("7000135"); + + Extension ext = new Extension(); + ext.setUrl("http://example.com/extensions#someext"); + ext.setValue(new DateTimeType("2011-01-02T11:13:15")); + + // Add the extension to the resource + patient.addExtension(ext); + // END SNIPPET: resourceExtension + + // START SNIPPET: resourceStringExtension + HumanName name = patient.addName(); + name.setFamily("Shmoe"); + StringType given = name.addGivenElement(); + given.setValue("Joe"); + Extension ext2 = new Extension().setUrl("http://examples.com#givenext").setValue(new StringType("given")); + given.addExtension(ext2); + + StringType given2 = name.addGivenElement(); + given2.setValue("Shmoe"); + Extension given2ext = new Extension().setUrl("http://examples.com#givenext_parent"); + given2.addExtension(given2ext); + Extension givenExtChild = new Extension(); + givenExtChild.setUrl("http://examples.com#givenext_child").setValue(new StringType("CHILD")); + given2ext.addExtension(givenExtChild); + // END SNIPPET: resourceStringExtension + + // START SNIPPET: subExtension + Extension parent = new Extension().setUrl("http://example.com#parent"); + patient.addExtension(parent); + + Extension child1 = new Extension().setUrl("http://example.com#child").setValue(new StringType("value1")); + parent.addExtension(child1); + + Extension child2 = new Extension().setUrl("http://example.com#child").setValue(new StringType("value1")); + parent.addExtension(child2); + // END SNIPPET: subExtension + + String output = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(patient); + ourLog.info(output); + + String enc = ourCtx.newXmlParser().encodeResourceToString(patient); + assertThat(enc, containsString("")); + assertThat(enc, containsString( + "")); + assertThat(enc, containsString("")); + assertThat(enc, containsString( + "")); + } + + @Test + public void testOmitResourceId() { + Patient p = new Patient(); + p.setId("123"); + p.addName().setFamily("ABC"); + + assertThat(ourCtx.newXmlParser().encodeResourceToString(p), stringContainsInOrder("123", "ABC")); + assertThat(ourCtx.newXmlParser().setOmitResourceId(true).encodeResourceToString(p), containsString("ABC")); + assertThat(ourCtx.newXmlParser().setOmitResourceId(true).encodeResourceToString(p), not(containsString("123"))); + } - @After - public void after() { - if (ourCtx == null) { - ourCtx = FhirContext.forDstu3(); - } - ourCtx.setNarrativeGenerator(null); - } - @Test public void testOverrideResourceIdWithBundleEntryFullUrlDisabled_ConfiguredOnFhirContext() { try { @@ -100,7 +2000,7 @@ public class XmlParserDstu3Test { ourCtx = null; } } - + @Test public void testOverrideResourceIdWithBundleEntryFullUrlDisabled_ConfiguredOnParser() { try { @@ -121,3143 +2021,1261 @@ public class XmlParserDstu3Test { } } - /** - * See #551 - */ - @Test - public void testXmlLargeAttribute() { - String largeString = StringUtils.leftPad("", (int) FileUtils.ONE_MB, 'A'); - - Patient p = new Patient(); - p.addName().setFamily(largeString); - - String encoded = ourCtx.newXmlParser().encodeResourceToString(p); - - p = ourCtx.newXmlParser().parseResource(Patient.class, encoded); - - assertEquals(largeString, p.getNameFirstRep().getFamily()); - } - - /** - * See #544 - */ - @Test - public void testBundleStitchReferencesByUuid() throws Exception { - Bundle bundle = new Bundle(); - - DocumentManifest dm = new DocumentManifest(); - dm.getSubject().setReference("urn:uuid:96e85cca-9797-45d6-834a-c4eb27f331d3"); - bundle.addEntry().setResource(dm); - - Patient patient = new Patient(); - patient.addName().setFamily("FAMILY"); - bundle.addEntry().setResource(patient).setFullUrl("urn:uuid:96e85cca-9797-45d6-834a-c4eb27f331d3"); - - String encoded = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(bundle); - ourLog.info(encoded); - - bundle = ourCtx.newXmlParser().parseResource(Bundle.class, encoded); - dm = (DocumentManifest) bundle.getEntry().get(0).getResource(); - - assertEquals("urn:uuid:96e85cca-9797-45d6-834a-c4eb27f331d3", dm.getSubject().getReference()); - - Patient subject = (Patient) dm.getSubject().getResource(); - assertNotNull(subject); - assertEquals("FAMILY", subject.getNameFirstRep().getFamily()); - } - - @Test - public void testBundleWithBinary() { - - String bundle = "\n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - ""; - - Bundle b = ourCtx.newXmlParser().parseResource(Bundle.class, bundle); - assertEquals(1, b.getEntry().size()); - - Binary bin = (Binary) b.getEntry().get(0).getResource(); - assertArrayEquals(new byte[] { 1, 2, 3, 4 }, bin.getContent()); - - } - - @Test - public void testContainedResourceInExtensionUndeclared() { - Patient p = new Patient(); - p.addName().setFamily("PATIENT"); - - Organization o = new Organization(); - o.setName("ORG"); - p.addExtension(new Extension("urn:foo", new Reference(o))); - - String str = ourCtx.newXmlParser().encodeResourceToString(p); - ourLog.info(str); - - p = ourCtx.newXmlParser().parseResource(Patient.class, str); - assertEquals("PATIENT", p.getName().get(0).getFamily()); - - List exts = p.getExtensionsByUrl("urn:foo"); - assertEquals(1, exts.size()); - Reference rr = (Reference) exts.get(0).getValue(); - o = (Organization) rr.getResource(); - assertEquals("ORG", o.getName()); - } - - @Test(expected = DataFormatException.class) - public void testContainedResourceWithNoId() throws IOException { - String string = IOUtils.toString(getClass().getResourceAsStream("/bundle_with_contained_with_no_id.xml"), StandardCharsets.UTF_8); - - IParser parser = ourCtx.newXmlParser(); - parser.setParserErrorHandler(new StrictErrorHandler()); - parser.parseResource(Bundle.class, string); - } - - @Test() - public void testContainedResourceWithNoIdLenient() throws IOException { - String string = IOUtils.toString(getClass().getResourceAsStream("/bundle_with_contained_with_no_id.xml"), StandardCharsets.UTF_8); - - IParser parser = ourCtx.newXmlParser(); - parser.setParserErrorHandler(new LenientErrorHandler()); - parser.parseResource(Bundle.class, string); - } - - @Test - public void testDuration() { - Encounter enc = new Encounter(); - Duration duration = new Duration(); - duration.setUnit("day").setValue(123L); - enc.setLength(duration); - - String str = ourCtx.newXmlParser().encodeResourceToString(enc); - ourLog.info(str); - - assertThat(str, not(containsString("meta"))); - assertThat(str, containsString("")); - } - - @Test - public void testEncodeAndParseBundleWithResourceRefs() { - - Patient pt = new Patient(); - pt.setId("patid"); - pt.addName().setFamily("PATIENT"); - - Organization org = new Organization(); - org.setId("orgid"); - org.setName("ORG"); - pt.getManagingOrganization().setResource(org); - - Bundle bundle = new Bundle(); - bundle.addEntry().setResource(pt); - bundle.addEntry().setResource(org); - - String encoded = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(bundle); - ourLog.info(encoded); - - assertThat(encoded, stringContainsInOrder( - "", - "", - "", - "")); - - bundle = ourCtx.newXmlParser().parseResource(Bundle.class, encoded); - pt = (Patient) bundle.getEntry().get(0).getResource(); - org = (Organization) bundle.getEntry().get(1).getResource(); - - assertEquals("Organization/orgid", org.getIdElement().getValue()); - assertEquals("Organization/orgid", pt.getManagingOrganization().getReferenceElement().getValue()); - assertSame(org, pt.getManagingOrganization().getResource()); - } - - @Test - public void testEncodeAndParseCompositeExtension() { - PatientWithCustomCompositeExtension pat = new PatientWithCustomCompositeExtension(); - pat.setId("123"); - pat.setFooParentExtension(new FooParentExtension()); - pat.getFooParentExtension().setChildA(new StringType("ValueA")); - pat.getFooParentExtension().setChildB(new StringType("ValueB")); - - String enc = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(pat); - ourLog.info(enc); - - pat = ourCtx.newXmlParser().parseResource(PatientWithCustomCompositeExtension.class, enc); - - assertEquals("ValueA", pat.getFooParentExtension().getChildA().getValue()); - assertEquals("ValueB", pat.getFooParentExtension().getChildB().getValue()); - } - - @Test - public void testEncodeAndParseContained() { - IParser xmlParser = ourCtx.newXmlParser().setPrettyPrint(true); - - // Create an organization, note that the organization does not have an ID - Organization org = new Organization(); - org.getNameElement().setValue("Contained Test Organization"); - - // Create a patient - Patient patient = new Patient(); - patient.setId("Patient/1333"); - patient.addIdentifier().setSystem("urn:mrns").setValue("253345"); - - // Put the organization as a reference in the patient resource - patient.getManagingOrganization().setResource(org); - - String encoded = xmlParser.encodeResourceToString(patient); - ourLog.info(encoded); - assertThat(encoded, containsString("")); - assertThat(encoded, containsString("")); - - // Create a bundle with just the patient resource - Bundle b = new Bundle(); - b.addEntry().setResource(patient); - - // Encode the bundle - encoded = xmlParser.encodeResourceToString(b); - ourLog.info(encoded); - assertThat(encoded, stringContainsInOrder(Arrays.asList("", "", ""))); - assertThat(encoded, containsString("")); - assertThat(encoded, stringContainsInOrder(Arrays.asList("", ""))); - assertThat(encoded, not(stringContainsInOrder(Arrays.asList("", "", "")))); - - // Re-parse the bundle - patient = (Patient) xmlParser.parseResource(xmlParser.encodeResourceToString(patient)); - assertEquals("#1", patient.getManagingOrganization().getReference()); - - assertNotNull(patient.getManagingOrganization().getResource()); - org = (Organization) patient.getManagingOrganization().getResource(); - assertEquals("#1", org.getIdElement().getValue()); - assertEquals("Contained Test Organization", org.getName()); - - // And re-encode a second time - encoded = xmlParser.encodeResourceToString(patient); - ourLog.info(encoded); - assertThat(encoded, stringContainsInOrder(Arrays.asList("", "", "", ""))); - assertThat(encoded, not(stringContainsInOrder(Arrays.asList("", "")))); - assertThat(encoded, containsString("")); - - // And re-encode once more, with the references cleared - patient.getContained().clear(); - patient.getManagingOrganization().setReference((String) null); - encoded = xmlParser.encodeResourceToString(patient); - ourLog.info(encoded); - assertThat(encoded, stringContainsInOrder(Arrays.asList("", "", "", ""))); - assertThat(encoded, not(stringContainsInOrder(Arrays.asList("", "")))); - assertThat(encoded, containsString("")); - - // And re-encode once more, with the references cleared and a manually set local ID - patient.getContained().clear(); - patient.getManagingOrganization().setReference((String) null); - patient.getManagingOrganization().getResource().setId(("#333")); - encoded = xmlParser.encodeResourceToString(patient); - ourLog.info(encoded); - assertThat(encoded, stringContainsInOrder(Arrays.asList("", "", "", ""))); - assertThat(encoded, not(stringContainsInOrder(Arrays.asList("", "")))); - - } - - @Test - public void testEncodeAndParseContainedCustomTypes() { - ourCtx = FhirContext.forDstu3(); - ourCtx.setDefaultTypeForProfile(CustomObservation.PROFILE, CustomObservation.class); - ourCtx.setDefaultTypeForProfile(CustomDiagnosticReport.PROFILE, CustomDiagnosticReport.class); - - CustomObservation obs = new CustomObservation(); - obs.setStatus(ObservationStatus.FINAL); - - CustomDiagnosticReport dr = new CustomDiagnosticReport(); - dr.setStatus(DiagnosticReportStatus.FINAL); - dr.addResult().setResource(obs); - - IParser parser = ourCtx.newXmlParser(); - parser.setPrettyPrint(true); - - String output = parser.encodeResourceToString(dr); - ourLog.info(output); - - assertThat(output, stringContainsInOrder( - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "")); - - /* - * Now PARSE! - */ - - dr = (CustomDiagnosticReport) parser.parseResource(output); - assertEquals(DiagnosticReportStatus.FINAL, dr.getStatus()); - - assertEquals("#1", dr.getResult().get(0).getReference()); - obs = (CustomObservation) dr.getResult().get(0).getResource(); - assertEquals(ObservationStatus.FINAL, obs.getStatus()); - - ourCtx = null; - } - - @Test - public void testEncodeAndParseContainedNonCustomTypes() { - ourCtx = FhirContext.forDstu3(); - - Observation obs = new Observation(); - obs.setStatus(ObservationStatus.FINAL); - - DiagnosticReport dr = new DiagnosticReport(); - dr.setStatus(DiagnosticReportStatus.FINAL); - dr.addResult().setResource(obs); - - IParser parser = ourCtx.newXmlParser(); - parser.setPrettyPrint(true); - - String output = parser.encodeResourceToString(dr); - ourLog.info(output); - - assertThat(output, stringContainsInOrder( - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "")); - - /* - * Now PARSE! - */ - - dr = (DiagnosticReport) parser.parseResource(output); - assertEquals(DiagnosticReportStatus.FINAL, dr.getStatus()); - - assertEquals("#1", dr.getResult().get(0).getReference()); - obs = (Observation) dr.getResult().get(0).getResource(); - assertEquals(ObservationStatus.FINAL, obs.getStatus()); - - ourCtx = null; - } - - @Test - public void testEncodeAndParseExtensionOnCode() { - Organization o = new Organization(); - o.setName("ORG"); - o.addExtension(new Extension("urn:foo", new CodeType("acode"))); - - String str = ourCtx.newXmlParser().encodeResourceToString(o); - ourLog.info(str); - assertThat(str, containsString("")); - - o = ourCtx.newXmlParser().parseResource(Organization.class, str); - - List exts = o.getExtensionsByUrl("urn:foo"); - assertEquals(1, exts.size()); - CodeType code = (CodeType) exts.get(0).getValue(); - assertEquals("acode", code.getValue()); - - } - - @Test - public void testEncodeAndParseExtensionOnReference() { - DataElement de = new DataElement(); - ElementDefinitionBindingComponent b = de.addElement().getBinding(); - b.setDescription("BINDING"); - - Organization o = new Organization(); - o.setName("ORG"); - b.addExtension(new Extension("urn:foo", new Reference(o))); - - String str = ourCtx.newXmlParser().encodeResourceToString(de); - ourLog.info(str); - - de = ourCtx.newXmlParser().parseResource(DataElement.class, str); - b = de.getElement().get(0).getBinding(); - assertEquals("BINDING", b.getDescription()); - - List exts = b.getExtensionsByUrl("urn:foo"); - assertEquals(1, exts.size()); - Reference rr = (Reference) exts.get(0).getValue(); - o = (Organization) rr.getResource(); - assertEquals("ORG", o.getName()); - - } - - @Test - public void testEncodeAndParseExtensions() throws Exception { - - Patient patient = new Patient(); - patient.addIdentifier().setUse(IdentifierUse.OFFICIAL).setSystem("urn:example").setValue("7000135"); - - Extension ext = new Extension(); - ext.setUrl("http://example.com/extensions#someext"); - ext.setValue(new DateTimeType("2011-01-02T11:13:15")); - patient.addExtension(ext); - - Extension parent = new Extension().setUrl("http://example.com#parent"); - patient.addExtension(parent); - Extension child1 = new Extension().setUrl("http://example.com#child").setValue(new StringType("value1")); - parent.addExtension(child1); - Extension child2 = new Extension().setUrl("http://example.com#child").setValue(new StringType("value2")); - parent.addExtension(child2); - - Extension modExt = new Extension(); - modExt.setUrl("http://example.com/extensions#modext"); - modExt.setValue(new DateType("1995-01-02")); - patient.addModifierExtension(modExt); - - HumanName name = patient.addName(); - name.setFamily("Blah"); - StringType given = name.addGivenElement(); - given.setValue("Joe"); - Extension ext2 = new Extension().setUrl("http://examples.com#givenext").setValue(new StringType("given")); - given.addExtension(ext2); - - StringType given2 = name.addGivenElement(); - given2.setValue("Shmoe"); - Extension given2ext = new Extension().setUrl("http://examples.com#givenext_parent"); - given2.addExtension(given2ext); - given2ext.addExtension(new Extension().setUrl("http://examples.com#givenext_child").setValue(new StringType("CHILD"))); - - String output = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(patient); - ourLog.info(output); - - String enc = ourCtx.newXmlParser().encodeResourceToString(patient); - assertThat(enc, containsString("")); - assertThat(enc, containsString("")); - assertThat(enc, containsString( - "")); - assertThat(enc, containsString("")); - assertThat(enc, containsString( - "")); - - /* - * Now parse this back - */ - - Patient parsed = ourCtx.newXmlParser().parseResource(Patient.class, enc); - ext = parsed.getExtension().get(0); - assertEquals("http://example.com/extensions#someext", ext.getUrl()); - assertEquals("2011-01-02T11:13:15", ((DateTimeType) ext.getValue()).getValueAsString()); - - parent = patient.getExtension().get(1); - assertEquals("http://example.com#parent", parent.getUrl()); - assertNull(parent.getValue()); - child1 = parent.getExtension().get(0); - assertEquals("http://example.com#child", child1.getUrl()); - assertEquals("value1", ((StringType) child1.getValue()).getValueAsString()); - child2 = parent.getExtension().get(1); - assertEquals("http://example.com#child", child2.getUrl()); - assertEquals("value2", ((StringType) child2.getValue()).getValueAsString()); - - modExt = parsed.getModifierExtension().get(0); - assertEquals("http://example.com/extensions#modext", modExt.getUrl()); - assertEquals("1995-01-02", ((DateType) modExt.getValue()).getValueAsString()); - - name = parsed.getName().get(0); - - ext2 = name.getGiven().get(0).getExtension().get(0); - assertEquals("http://examples.com#givenext", ext2.getUrl()); - assertEquals("given", ((StringType) ext2.getValue()).getValueAsString()); - - given2ext = name.getGiven().get(1).getExtension().get(0); - assertEquals("http://examples.com#givenext_parent", given2ext.getUrl()); - assertNull(given2ext.getValue()); - Extension given2ext2 = given2ext.getExtension().get(0); - assertEquals("http://examples.com#givenext_child", given2ext2.getUrl()); - assertEquals("CHILD", ((StringType) given2ext2.getValue()).getValue()); - - } - - /** - * See #216 - */ - @Test - public void testEncodeAndParseIdentifierDstu2() { - IParser xmlParser = ourCtx.newXmlParser().setPrettyPrint(true); - - Patient patient = new Patient(); - patient.addIdentifier().setSystem("SYS").setValue("VAL").setType(new CodeableConcept().addCoding(new Coding().setSystem("http://hl7.org/fhir/v2/0203").setCode("MR"))); - - String out = xmlParser.encodeResourceToString(patient); - ourLog.info(out); - - assertThat(out, stringContainsInOrder("", - "", - "", - "", - "", - "", - "", - "", - "", - "")); - - patient = ourCtx.newXmlParser().parseResource(Patient.class, out); - assertEquals("http://hl7.org/fhir/v2/0203", patient.getIdentifier().get(0).getType().getCoding().get(0).getSystem()); - assertEquals("MR", patient.getIdentifier().get(0).getType().getCoding().get(0).getCode()); - } - - /** - * See #347 - */ - @Test - public void testEncodeAndParseMedicationRequest() { - MedicationRequest mo = new MedicationRequest(); - mo.getAuthoredOnElement().setValueAsString("2015-10-05"); - - String encoded = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(mo); - ourLog.info(encoded); - - mo = ourCtx.newXmlParser().parseResource(MedicationRequest.class, encoded); - assertEquals("2015-10-05", mo.getAuthoredOnElement().getValueAsString()); - } - - @Test - public void testEncodeAndParseMetaProfileAndTags() { - Patient p = new Patient(); - p.addName().setFamily("FAMILY"); - - p.getMeta().addProfile("http://foo/Profile1"); - p.getMeta().addProfile("http://foo/Profile2"); - - p.getMeta().addTag().setSystem("scheme1").setCode("term1").setDisplay("label1"); - p.getMeta().addTag().setSystem("scheme2").setCode("term2").setDisplay("label2"); - - p.getMeta().addSecurity().setSystem("sec_scheme1").setCode("sec_term1").setDisplay("sec_label1"); - p.getMeta().addSecurity().setSystem("sec_scheme2").setCode("sec_term2").setDisplay("sec_label2"); - - String enc = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(p); - ourLog.info(enc); - - assertThat(enc, stringContainsInOrder("", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "")); - - Patient parsed = ourCtx.newXmlParser().parseResource(Patient.class, enc); - List gotLabels = parsed.getMeta().getProfile(); - assertEquals(2, gotLabels.size()); - UriType label = gotLabels.get(0); - assertEquals("http://foo/Profile1", label.getValue()); - label = gotLabels.get(1); - assertEquals("http://foo/Profile2", label.getValue()); - - List tagList = parsed.getMeta().getTag(); - assertEquals(2, tagList.size()); - assertEquals("scheme1", tagList.get(0).getSystem()); - assertEquals("term1", tagList.get(0).getCode()); - assertEquals("label1", tagList.get(0).getDisplay()); - assertEquals("scheme2", tagList.get(1).getSystem()); - assertEquals("term2", tagList.get(1).getCode()); - assertEquals("label2", tagList.get(1).getDisplay()); - - tagList = parsed.getMeta().getSecurity(); - assertEquals(2, tagList.size()); - assertEquals("sec_scheme1", tagList.get(0).getSystem()); - assertEquals("sec_term1", tagList.get(0).getCode()); - assertEquals("sec_label1", tagList.get(0).getDisplay()); - assertEquals("sec_scheme2", tagList.get(1).getSystem()); - assertEquals("sec_term2", tagList.get(1).getCode()); - assertEquals("sec_label2", tagList.get(1).getDisplay()); - } - - @Test - public void testEncodeAndParseMetaProfiles() { - Patient p = new Patient(); - p.addName().setFamily("FAMILY"); - - p.getMeta().addTag().setSystem("scheme1").setCode("term1").setDisplay("label1"); - p.getMeta().addTag().setSystem("scheme2").setCode("term2").setDisplay("label2"); - - String enc = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(p); - ourLog.info(enc); - - assertThat(enc, stringContainsInOrder("", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "")); - - Patient parsed = ourCtx.newXmlParser().parseResource(Patient.class, enc); - assertThat(parsed.getMeta().getProfile(), empty()); - - List tagList = parsed.getMeta().getTag(); - assertEquals(2, tagList.size()); - assertEquals("scheme1", tagList.get(0).getSystem()); - assertEquals("term1", tagList.get(0).getCode()); - assertEquals("label1", tagList.get(0).getDisplay()); - assertEquals("scheme2", tagList.get(1).getSystem()); - assertEquals("term2", tagList.get(1).getCode()); - assertEquals("label2", tagList.get(1).getDisplay()); - } - - /** - * See #336 - */ - @Test - public void testEncodeAndParseNullPrimitiveWithExtensions() { - - Patient p = new Patient(); - p.setId("patid"); - HumanName name = p.addName(); - name.addGivenElement().setValue(null).setId("f0").addExtension(new Extension("http://foo", new StringType("FOOEXT0"))); - name.addGivenElement().setValue("V1").setId("f1").addExtension((Extension) new Extension("http://foo", new StringType("FOOEXT1")).setId("ext1id")); - name.addGivenElement(); // this one shouldn't get encoded - name.addGivenElement().setValue(null).addExtension(new Extension("http://foo", new StringType("FOOEXT3"))); - name.setId("nameid"); - - String output = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(p); - ourLog.info(output); - - output = ourCtx.newXmlParser().setPrettyPrint(false).encodeResourceToString(p); - String expected = ""; - - ourLog.info("Expected: {}", expected); - ourLog.info("Actual : {}", output); - - assertEquals(expected, output); - - p = ourCtx.newXmlParser().parseResource(Patient.class, output); - assertEquals("patid", p.getIdElement().getIdPart()); - - name = p.getName().get(0); - assertEquals("nameid", name.getId()); - assertEquals(3, name.getGiven().size()); - - assertEquals(null, name.getGiven().get(0).getValue()); - assertEquals("V1", name.getGiven().get(1).getValue()); - assertEquals(null, name.getGiven().get(2).getValue()); - - assertEquals("f0", name.getGiven().get(0).getId()); - assertEquals("f1", name.getGiven().get(1).getId()); - assertEquals(null, name.getGiven().get(2).getId()); - - assertEquals(1, name.getGiven().get(0).getExtension().size()); - assertEquals("http://foo", name.getGiven().get(0).getExtension().get(0).getUrl()); - assertEquals("FOOEXT0", ((StringType) name.getGiven().get(0).getExtension().get(0).getValue()).getValue()); - assertEquals(null, name.getGiven().get(0).getExtension().get(0).getId()); - - assertEquals(1, name.getGiven().get(1).getExtension().size()); - assertEquals("http://foo", name.getGiven().get(1).getExtension().get(0).getUrl()); - assertEquals("FOOEXT1", ((StringType) name.getGiven().get(1).getExtension().get(0).getValue()).getValue()); - assertEquals("ext1id", name.getGiven().get(1).getExtension().get(0).getId()); - - assertEquals(1, name.getGiven().get(2).getExtension().size()); - assertEquals("http://foo", name.getGiven().get(2).getExtension().get(0).getUrl()); - assertEquals("FOOEXT3", ((StringType) name.getGiven().get(2).getExtension().get(0).getValue()).getValue()); - assertEquals(null, name.getGiven().get(2).getExtension().get(0).getId()); - - } - - @Test - public void testEncodeAndParseProfiledDatatype() { - MedicationRequest mo = new MedicationRequest(); - mo.addDosageInstruction().getTiming().getRepeat().setBounds(new Duration().setCode("code")); - String out = ourCtx.newXmlParser().encodeResourceToString(mo); - ourLog.info(out); - assertThat(out, containsString("")); - - mo = ourCtx.newXmlParser().parseResource(MedicationRequest.class, out); - Duration duration = (Duration) mo.getDosageInstruction().get(0).getTiming().getRepeat().getBounds(); - assertEquals("code", duration.getCode()); - } - - /** - * See #216 - Profiled datatypes should use their unprofiled parent type as the choice[x] name - */ - @Test - public void testEncodeAndParseProfiledDatatypeChoice() throws Exception { - IParser xmlParser = ourCtx.newXmlParser(); - - MedicationStatement ms = new MedicationStatement(); - ms.addDosage().setDose(new SimpleQuantity().setValue(123)); - - String output = xmlParser.encodeResourceToString(ms); - assertThat(output, containsString("")); - } - - @Test - public void testEncodeAndParseSecurityLabels() { - Patient p = new Patient(); - p.addName().setFamily("FAMILY"); - - List labels = new ArrayList(); - labels.add(new Coding().setSystem("SYSTEM1").setCode("CODE1").setDisplay("DISPLAY1").setVersion("VERSION1")); - labels.add(new Coding().setSystem("SYSTEM2").setCode("CODE2").setDisplay("DISPLAY2").setVersion("VERSION2")); - p.getMeta().getSecurity().addAll(labels); - - String enc = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(p); - ourLog.info(enc); - - assertThat(enc, stringContainsInOrder("", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "")); - - Patient parsed = ourCtx.newXmlParser().parseResource(Patient.class, enc); - List gotLabels = parsed.getMeta().getSecurity(); - - assertEquals(2, gotLabels.size()); - - Coding label = gotLabels.get(0); - assertEquals("SYSTEM1", label.getSystem()); - assertEquals("CODE1", label.getCode()); - assertEquals("DISPLAY1", label.getDisplay()); - assertEquals("VERSION1", label.getVersion()); - - label = gotLabels.get(1); - assertEquals("SYSTEM2", label.getSystem()); - assertEquals("CODE2", label.getCode()); - assertEquals("DISPLAY2", label.getDisplay()); - assertEquals("VERSION2", label.getVersion()); - } - - /** - * See #103 - */ - @Test - public void testEncodeAndReEncodeContainedJson() { - Composition comp = new Composition(); - comp.addSection().addEntry().setResource(new AllergyIntolerance().addNote(new Annotation().setText("Section0_Allergy0"))); - comp.addSection().addEntry().setResource(new AllergyIntolerance().addNote(new Annotation().setText("Section1_Allergy0"))); - comp.addSection().addEntry().setResource(new AllergyIntolerance().addNote(new Annotation().setText("Section2_Allergy0"))); - - IParser parser = ourCtx.newJsonParser().setPrettyPrint(true); - - String string = parser.encodeResourceToString(comp); - ourLog.info(string); - - Composition parsed = parser.parseResource(Composition.class, string); - parsed.getSection().remove(0); - - string = parser.encodeResourceToString(parsed); - ourLog.info(string); - - parsed = parser.parseResource(Composition.class, string); - assertEquals(2, parsed.getContained().size()); - } - - /** - * See #103 - */ - @Test - public void testEncodeAndReEncodeContainedXml() { - Composition comp = new Composition(); - comp.addSection().addEntry().setResource(new AllergyIntolerance().addNote(new Annotation().setText("Section0_Allergy0"))); - comp.addSection().addEntry().setResource(new AllergyIntolerance().addNote(new Annotation().setText("Section1_Allergy0"))); - comp.addSection().addEntry().setResource(new AllergyIntolerance().addNote(new Annotation().setText("Section2_Allergy0"))); - - IParser parser = ourCtx.newXmlParser().setPrettyPrint(true); - - String string = parser.encodeResourceToString(comp); - ourLog.info(string); - - Composition parsed = parser.parseResource(Composition.class, string); - parsed.getSection().remove(0); - - string = parser.encodeResourceToString(parsed); - ourLog.info(string); - - parsed = parser.parseResource(Composition.class, string); - assertEquals(2, parsed.getContained().size()); - } - - @Test - public void testEncodeBinaryWithNoContentType() { - Binary b = new Binary(); - b.setContent(new byte[] { 1, 2, 3, 4 }); - - String output = ourCtx.newXmlParser().encodeResourceToString(b); - ourLog.info(output); - - assertEquals("", output); - } - - @Test - public void testEncodeBundleWithContained() { - DiagnosticReport rpt = new DiagnosticReport(); - rpt.addResult().setResource(new Observation().setCode(new CodeableConcept().setText("Sharp1")).setId("#1")); - rpt.addResult().setResource(new Observation().setCode(new CodeableConcept().setText("Uuid1")).setId("urn:uuid:UUID1")); - - Bundle b = new Bundle(); - b.addEntry().setResource(rpt); - - String encoded = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(b); - ourLog.info(encoded); - - assertThat(encoded, stringContainsInOrder("", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "")); - - } - - /** - * See #113 - */ - @Test - public void testEncodeContainedResources() { - - MedicationRequest medicationPrescript = new MedicationRequest(); - - String medId = "123"; - CodeableConcept codeDt = new CodeableConcept().addCoding(new Coding().setSystem("urn:sys").setCode("code1")); - - // Adding medication to Contained. - Medication medResource = new Medication(); - medResource.setCode(codeDt); - medResource.setId("#" + String.valueOf(medId)); - medicationPrescript.getContained().add(medResource); - - // Medication reference. This should point to the contained resource. - Reference medRefDt = new Reference("#" + medId); - medRefDt.setDisplay("MedRef"); - medicationPrescript.setMedication(medRefDt); - - IParser p = ourCtx.newXmlParser().setPrettyPrint(true); - String encoded = p.encodeResourceToString(medicationPrescript); - ourLog.info(encoded); - - // @formatter:on - assertThat(encoded, - stringContainsInOrder("", "", "", "", "", "", - "", "", "", "", "", "", "", "", - "", "", "")); - - } - - /** - * See #113 - */ - @Test - public void testEncodeContainedResourcesAutomatic() { - - MedicationRequest medicationPrescript = new MedicationRequest(); - String nameDisp = "MedRef"; - CodeableConcept codeDt = new CodeableConcept().addCoding(new Coding("urn:sys", "code1", null)); - - // Adding medication to Contained. - Medication medResource = new Medication(); - // No ID set - medResource.setCode(codeDt); - - // Medication reference. This should point to the contained resource. - Reference medRefDt = new Reference(); - medRefDt.setDisplay(nameDisp); - // Resource reference set, but no ID - medRefDt.setResource(medResource); - medicationPrescript.setMedication(medRefDt); - - IParser p = ourCtx.newXmlParser().setPrettyPrint(true); - String encoded = p.encodeResourceToString(medicationPrescript); - ourLog.info(encoded); - - assertThat(encoded, - stringContainsInOrder("", "", "", "", "", "", - "", "", "", "", "", "", "", "", - "", "", "")); - - } - - /** - * See #113 - */ - @Test - public void testEncodeContainedResourcesManualContainUsingNonLocalId() { - - MedicationRequest medicationPrescript = new MedicationRequest(); - - String medId = "123"; - CodeableConcept codeDt = new CodeableConcept().addCoding(new Coding("urn:sys", "code1", null)); - - // Adding medication to Contained. - Medication medResource = new Medication(); - medResource.setCode(codeDt); - medResource.setId(String.valueOf(medId)); // ID does not start with '#' - medicationPrescript.getContained().add(medResource); - - // Medication reference. This should point to the contained resource. - Reference medRefDt = new Reference("#" + medId); - medRefDt.setDisplay("MedRef"); - medicationPrescript.setMedication(medRefDt); - - IParser p = ourCtx.newXmlParser().setPrettyPrint(true); - String encoded = p.encodeResourceToString(medicationPrescript); - ourLog.info(encoded); - - assertThat(encoded, - stringContainsInOrder("", "", "", "", "", "", - "", "", "", "", "", "", "", "", - "", "", "")); - - } - - @Test - public void testEncodeContainedWithNarrativeIsSuppresed() throws Exception { - IParser parser = ourCtx.newXmlParser().setPrettyPrint(true); - - // Create an organization, note that the organization does not have an ID - Organization org = new Organization(); - org.getNameElement().setValue("Contained Test Organization"); - org.getText().setDivAsString("
FOOBAR
"); - - // Create a patient - Patient patient = new Patient(); - patient.setId("Patient/1333"); - patient.addIdentifier().setSystem("urn:mrns").setValue("253345"); - patient.getText().setDivAsString("
BARFOO
"); - patient.getManagingOrganization().setResource(org); - - String encoded = parser.encodeResourceToString(patient); - ourLog.info(encoded); - - assertThat(encoded, stringContainsInOrder("", "
BARFOO
", "", "", "", "")); - assertThat(encode, stringContainsInOrder("\n\n

A P TAG

line1\nline2\nline3  BOLD

"); - - String output = ourCtx.newXmlParser().setPrettyPrint(false).encodeResourceToString(p); - ourLog.info(output); - - assertThat(output, stringContainsInOrder( - "A P TAG

", - "

line1\nline2\nline3  BOLD
")); - - } - - @Test - public void testEncodeDivWithPrePrettyPrint() { - - Patient p = new Patient(); - p.getText().setDivAsString("
\n\n

A P TAG

line1\nline2\nline3  BOLD

"); - - String output = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(p); - ourLog.info(output); - - assertThat(output, stringContainsInOrder( - " ", - " line1\nline2\nline3 BOLD")); - - } - - @Test - public void testEncodeDoesntIncludeUuidId() { - Patient p = new Patient(); - p.setId(new IdType("urn:uuid:42795ed8-041f-4ebf-b6f4-78ef6f64c2f2")); - p.addIdentifier().setSystem("ACME"); - - String actual = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(p); - assertThat(actual, not(containsString("78ef6f64c2f2"))); - } - - @Test - public void testEncodeEmptyBinary() { - String output = ourCtx.newXmlParser().encodeResourceToString(new Binary()); - assertEquals("", output); - } - - /** - * #158 - */ - @Test - public void testEncodeEmptyTag() { - ArrayList tagList = new ArrayList(); - tagList.add(new Coding()); - tagList.add(new Coding().setDisplay("Label")); - - Patient p = new Patient(); - p.getMeta().getTag().addAll(tagList); - - String encoded = ourCtx.newXmlParser().encodeResourceToString(p); - assertThat(encoded, not(containsString("tag"))); - } - - /** - * #158 - */ - @Test - public void testEncodeEmptyTag2() { - ArrayList tagList = new ArrayList(); - tagList.add(new Coding().setSystem("scheme").setCode("code")); - tagList.add(new Coding().setDisplay("Label")); - - Patient p = new Patient(); - p.getMeta().getTag().addAll(tagList); - - String encoded = ourCtx.newXmlParser().encodeResourceToString(p); - assertThat(encoded, containsString("tag")); - assertThat(encoded, containsString("scheme")); - assertThat(encoded, not(containsString("Label"))); - } - - @Test - public void testEncodeExtensionUndeclaredNonModifier() { - Observation obs = new Observation(); - obs.setId("1"); - obs.getMeta().addProfile("http://profile"); - Extension ext = obs.addExtension(); - ext.setUrl("http://exturl").setValue(new StringType("ext_url_value")); - - obs.getCode().setText("CODE"); - - IParser parser = ourCtx.newXmlParser(); - - String output = parser.setPrettyPrint(true).encodeResourceToString(obs); - ourLog.info(output); - - assertThat(output, stringContainsInOrder( - "", - "", - "", - "", - "", - "")); - assertThat(output, not(stringContainsInOrder( - ""))); - - obs = parser.parseResource(Observation.class, output); - assertEquals(1, obs.getExtension().size()); - assertEquals("http://exturl", obs.getExtension().get(0).getUrl()); - assertEquals("ext_url_value", ((StringType) obs.getExtension().get(0).getValue()).getValue()); - } - - @Test - public void testEncodeExtensionUndeclaredNonModifierWithChildExtension() { - Observation obs = new Observation(); - obs.setId("1"); - obs.getMeta().addProfile("http://profile"); - Extension ext = obs.addExtension(); - ext.setUrl("http://exturl"); - - Extension subExt = ext.addExtension(); - subExt.setUrl("http://subext").setValue(new StringType("sub_ext_value")); - - obs.getCode().setText("CODE"); - - IParser parser = ourCtx.newXmlParser(); - - String output = parser.setPrettyPrint(true).encodeResourceToString(obs); - ourLog.info(output); - - assertThat(output, stringContainsInOrder( - "", - "", - "", - "", - "", - "", - "")); - assertThat(output, not(stringContainsInOrder( - ""))); - - obs = parser.parseResource(Observation.class, output); - assertEquals(1, obs.getExtension().size()); - assertEquals("http://exturl", obs.getExtension().get(0).getUrl()); - assertEquals(1, obs.getExtension().get(0).getExtension().size()); - assertEquals("http://subext", obs.getExtension().get(0).getExtension().get(0).getUrl()); - assertEquals("sub_ext_value", ((StringType) obs.getExtension().get(0).getExtension().get(0).getValue()).getValue()); - } - - /** - * See #327 - */ - @Test - public void testEncodeExtensionWithContainedResource() { - - TestPatientFor327 patient = new TestPatientFor327(); - patient.setBirthDateElement(new DateType("2016-04-14")); - - List conditions = new ArrayList(); - Condition condition = new Condition(); - condition.addBodySite().setText("BODY SITE"); - conditions.add(new Reference(condition)); - patient.setCondition(conditions); - - String encoded = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(patient); - ourLog.info(encoded); - - assertThat(encoded, stringContainsInOrder( - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "")); - - } - - @Test - public void testEncodeExtensionWithResourceContent() { - IParser parser = ourCtx.newXmlParser(); - - Patient patient = new Patient(); - patient.addAddress().setUse(AddressUse.HOME); - patient.addExtension(new Extension("urn:foo", new Reference("Organization/123"))); - - String val = parser.encodeResourceToString(patient); - ourLog.info(val); - assertThat(val, StringContains.containsString("")); - - Patient actual = parser.parseResource(Patient.class, val); - assertEquals(AddressUse.HOME, patient.getAddress().get(0).getUse()); - List ext = actual.getExtension(); - assertEquals(1, ext.size()); - Reference ref = (Reference) ext.get(0).getValue(); - assertEquals("Organization/123", ref.getReference()); - - } - - @Test - public void testEncodeHistoryEncodeVersionsAtPath3() { - ourCtx = FhirContext.forDstu3(); - - assertNull(ourCtx.newXmlParser().getStripVersionsFromReferences()); - - AuditEvent auditEvent = new AuditEvent(); - auditEvent.addEntity().setReference(new Reference("http://foo.com/Organization/2/_history/1")); - - IParser parser = ourCtx.newXmlParser(); - - parser.setDontStripVersionsFromReferencesAtPaths("AuditEvent.entity.reference"); - String enc = parser.setPrettyPrint(true).encodeResourceToString(auditEvent); - ourLog.info(enc); - assertThat(enc, containsString("")); - - parser.setDontStripVersionsFromReferencesAtPaths(new ArrayList()); - enc = parser.setPrettyPrint(true).encodeResourceToString(auditEvent); - ourLog.info(enc); - assertThat(enc, containsString("")); - - parser.setDontStripVersionsFromReferencesAtPaths((String[]) null); - enc = parser.setPrettyPrint(true).encodeResourceToString(auditEvent); - ourLog.info(enc); - assertThat(enc, containsString("")); - - parser.setDontStripVersionsFromReferencesAtPaths((List) null); - enc = parser.setPrettyPrint(true).encodeResourceToString(auditEvent); - ourLog.info(enc); - assertThat(enc, containsString("")); - - } - - @Test - public void testEncodeNarrativeSuppressed() { - Patient patient = new Patient(); - patient.setId("Patient/1/_history/1"); - patient.getText().setDivAsString("
THE DIV
"); - patient.addName().setFamily("FAMILY"); - patient.setMaritalStatus(new CodeableConcept().addCoding(new Coding().setCode("D"))); - patient.setMaritalStatus(new CodeableConcept().addCoding(new Coding().setCode("D"))); - - String encoded = ourCtx.newXmlParser().setPrettyPrint(true).setSuppressNarratives(true).encodeResourceToString(patient); - ourLog.info(encoded); - - assertThat(encoded, containsString("", "", "", "")); - assertThat(encoded, not(containsString("text"))); - assertThat(encoded, not(containsString("THE DIV"))); - assertThat(encoded, containsString("family")); - assertThat(encoded, containsString("maritalStatus")); - } - - @Test - public void testEncodeNonContained() { - // Create an organization - Organization org = new Organization(); - org.setId("Organization/65546"); - org.getNameElement().setValue("Contained Test Organization"); - - // Create a patient - Patient patient = new Patient(); - patient.setId("Patient/1333"); - patient.addIdentifier().setSystem("urn:mrns").setValue("253345"); - patient.getManagingOrganization().setResource(org); - - // Create a list containing both resources. In a server method, you might just - // return this list, but here we will create a bundle to encode. - List resources = new ArrayList(); - resources.add(org); - resources.add(patient); - - // Create a bundle with both - Bundle b = new Bundle(); - b.addEntry().setResource(org); - b.addEntry().setResource(patient); - - // Encode the buntdle - String encoded = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(b); - ourLog.info(encoded); - assertThat(encoded, not(containsString(""))); - assertThat(encoded, stringContainsInOrder("", "")); - assertThat(encoded, containsString("")); - assertThat(encoded, stringContainsInOrder("", "")); - - encoded = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(patient); - ourLog.info(encoded); - assertThat(encoded, not(containsString(""))); - assertThat(encoded, containsString("")); - - } - - /** - * See #312 - */ - @Test - public void testEncodeNullElement() { - Patient patient = new Patient(); - patient.addName().getGiven().add(null); - - IParser parser = ourCtx.newXmlParser(); - String xml = parser.encodeResourceToString(patient); - - ourLog.info(xml); - assertEquals("", xml); - } - - /** - * See #312 - */ - @Test - public void testEncodeNullExtension() { - Patient patient = new Patient(); - patient.getExtension().add(null); // Purposely add null - patient.getModifierExtension().add(null); // Purposely add null - patient.getExtension().add(new Extension("http://hello.world", new StringType("Hello World"))); - patient.getName().add(null); - patient.addName().getGiven().add(null); - - IParser parser = ourCtx.newXmlParser(); - String xml = parser.encodeResourceToString(patient); - - ourLog.info(xml); - assertEquals("", xml); - } - - @Test - public void testEncodeReferenceUsingUnqualifiedResourceWorksCorrectly() { - - Patient patient = new Patient(); - patient.setId("phitcc_pat_normal"); - patient.addName().addGiven("Patty").setUse(NameUse.NICKNAME); - patient.addTelecom().setSystem(ContactPointSystem.EMAIL).setValue("patpain@ehealthinnovation.org"); - patient.setGender(AdministrativeGender.FEMALE); - patient.setBirthDateElement(new DateType("2001-10-13")); - - DateTimeType obsEffectiveTime = new DateTimeType("2015-04-11T12:22:01-04:00"); - - Observation obsParent = new Observation(); - obsParent.setId("phitcc_obs_bp_parent"); - obsParent.getSubject().setResource(patient); - obsParent.setStatus(ObservationStatus.FINAL); - obsParent.setEffective(obsEffectiveTime); - - Observation obsSystolic = new Observation(); - obsSystolic.setId("phitcc_obs_bp_dia"); - obsSystolic.getSubject().setResource(patient); - obsSystolic.setEffective(obsEffectiveTime); - obsParent.addRelated().setType(ObservationRelationshipType.HASMEMBER).setTarget(new Reference(obsSystolic)); - - Observation obsDiastolic = new Observation(); - obsDiastolic.setId("phitcc_obs_bp_dia"); - obsDiastolic.getSubject().setResource(patient); - obsDiastolic.setEffective(obsEffectiveTime); - obsParent.addRelated().setType(ObservationRelationshipType.HASMEMBER).setTarget(new Reference(obsDiastolic)); - - String str = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(obsParent); - ourLog.info(str); - - assertThat(str, containsString("")); - assertThat(str, containsString("")); - } - - @Test - public void testEncodeReferenceWithUuid() { - - Practitioner pract = new Practitioner(); - pract.setId(IdType.newRandomUuid()); - pract.addName().setFamily("PRACT FAMILY"); - - Patient patient = new Patient(); - patient.addGeneralPractitioner().setResource(pract); - - String encoded = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(patient); - ourLog.info(encoded); - - assertThat(pract.getId(), startsWith("urn:uuid:")); - assertThat(encoded, containsString("")); - } - - @Test - public void testEncodeSummary() { - Patient patient = new Patient(); - patient.setId("Patient/1/_history/1"); - patient.getText().setDivAsString("
THE DIV
"); - patient.addName().setFamily("FAMILY"); - patient.setMaritalStatus(new CodeableConcept().addCoding(new Coding().setCode("D"))); - - String encoded = ourCtx.newXmlParser().setPrettyPrint(true).setSummaryMode(true).encodeResourceToString(patient); - ourLog.info(encoded); - - assertThat(encoded, containsString("", "", "", "")); - assertThat(encoded, not(containsString("THE DIV"))); - assertThat(encoded, containsString("family")); - assertThat(encoded, not(containsString("maritalStatus"))); - } - - @Test - public void testEncodeSummary2() { - Patient patient = new Patient(); - patient.setId("Patient/1/_history/1"); - patient.getText().setDivAsString("
THE DIV
"); - patient.addName().setFamily("FAMILY"); - patient.setMaritalStatus(new CodeableConcept().addCoding(new Coding().setCode("D"))); - - patient.getMeta().addTag().setSystem("foo").setCode("bar"); - - String encoded = ourCtx.newXmlParser().setPrettyPrint(true).setSummaryMode(true).encodeResourceToString(patient); - ourLog.info(encoded); - - assertThat(encoded, containsString("", "", "", "")); - assertThat(encoded, stringContainsInOrder("", "", "", "")); - assertThat(encoded, not(containsString("THE DIV"))); - assertThat(encoded, containsString("family")); - assertThat(encoded, not(containsString("maritalStatus"))); - } - - @Test - public void testEncodeUndeclaredBlock() throws Exception { - FooMessageHeader.FooMessageSourceComponent source = new FooMessageHeader.FooMessageSourceComponent(); - source.getMessageHeaderApplicationId().setValue("APPID"); - source.setName("NAME"); - - FooMessageHeader header = new FooMessageHeader(); - header.setSource(source); - - header.addDestination().setName("DEST"); - - Bundle bundle = new Bundle(); - bundle.addEntry().setResource(header); - - IParser p = ourCtx.newXmlParser(); - p.setPrettyPrint(true); - - String encode = p.encodeResourceToString(bundle); - ourLog.info(encode); - - assertThat(encode, containsString("")); - assertThat(encode, stringContainsInOrder(" fact = new AddressUseEnumFactory(); - PrimitiveType enumeration = new Enumeration(fact).setValue(AddressUse.HOME); - patient.addExtension().setUrl("urn:foo").setValue(enumeration); - - String val = parser.encodeResourceToString(patient); - ourLog.info(val); - assertThat(val, StringContains.containsString("")); - - MyPatientWithOneDeclaredEnumerationExtensionDstu3 actual = parser.parseResource(MyPatientWithOneDeclaredEnumerationExtensionDstu3.class, val); - assertEquals(AddressUse.HOME, patient.getAddress().get(0).getUse()); - Enumeration ref = actual.getFoo(); - assertEquals("home", ref.getValue().toCode()); - - } - - @Test - public void testEncodeWithContained() { - List contained = new ArrayList(); - - // Will be added by reference - Patient p = new Patient(); - p.setId("#" + "1000"); - contained.add(p); - - // Will be added by direct resource object - Location l = new Location(); - l.setId("#" + "1001"); - contained.add(l); - - // Will not be referred to (and therefore shouldn't appear in output) - Location l2 = new Location(); - l2.setId("#1002"); - contained.add(l2); - - Appointment appointment = new Appointment(); - appointment.setId("1234"); - appointment.getContained().addAll(contained); - - appointment.addParticipant().getActor().setReference("#1000"); - appointment.addParticipant().getActor().setResource(l); - - String encoded = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(appointment); - ourLog.info(encoded); - - assertThat(encoded, stringContainsInOrder( - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "")); - - assertThat(encoded, not(containsString("#1002"))); - } - - @Test - public void testEncodeWithDontEncodeElements() throws Exception { - Patient patient = new Patient(); - patient.setId("123"); - patient.getMeta().addProfile("http://profile"); - patient.addName().setFamily("FAMILY").addGiven("GIVEN"); - patient.addAddress().addLine("LINE1"); - - { - IParser p = ourCtx.newXmlParser(); - p.setDontEncodeElements(Sets.newHashSet("*.meta", "*.id")); - p.setPrettyPrint(true); - String out = p.encodeResourceToString(patient); - ourLog.info(out); - assertThat(out, containsString("Patient")); - assertThat(out, containsString("name")); - assertThat(out, containsString("address")); - assertThat(out, not(containsString("id"))); - assertThat(out, not(containsString("meta"))); - } - { - IParser p = ourCtx.newXmlParser(); - p.setDontEncodeElements(Sets.newHashSet("Patient.meta", "Patient.id")); - p.setPrettyPrint(true); - String out = p.encodeResourceToString(patient); - ourLog.info(out); - assertThat(out, containsString("Patient")); - assertThat(out, containsString("name")); - assertThat(out, containsString("address")); - assertThat(out, not(containsString("id"))); - assertThat(out, not(containsString("meta"))); - } - { - IParser p = ourCtx.newXmlParser(); - p.setDontEncodeElements(Sets.newHashSet("Patient.name.family")); - p.setPrettyPrint(true); - String out = p.encodeResourceToString(patient); - ourLog.info(out); - assertThat(out, containsString("GIVEN")); - assertThat(out, not(containsString("FAMILY"))); - } - { - IParser p = ourCtx.newXmlParser(); - p.setDontEncodeElements(Sets.newHashSet("*.meta", "*.id")); - p.setPrettyPrint(true); - String out = p.encodeResourceToString(patient); - ourLog.info(out); - assertThat(out, containsString("Patient")); - assertThat(out, containsString("name")); - assertThat(out, containsString("address")); - assertThat(out, not(containsString("id"))); - assertThat(out, not(containsString("meta"))); - } - { - IParser p = ourCtx.newXmlParser(); - p.setDontEncodeElements(Sets.newHashSet("Patient.meta")); - p.setEncodeElements(new HashSet(Arrays.asList("Patient.name"))); - p.setPrettyPrint(true); - String out = p.encodeResourceToString(patient); - ourLog.info(out); - assertThat(out, containsString("Patient")); - assertThat(out, containsString("name")); - assertThat(out, containsString("id")); - assertThat(out, not(containsString("address"))); - assertThat(out, not(containsString("meta"))); - } - } - - @Test - public void testEncodeWithEncodeElements() throws Exception { - Patient patient = new Patient(); - patient.getMeta().addProfile("http://profile"); - patient.addName().setFamily("FAMILY"); - patient.addAddress().addLine("LINE1"); - - Bundle bundle = new Bundle(); - bundle.setTotal(100); - bundle.addEntry().setResource(patient); - - { - IParser p = ourCtx.newXmlParser(); - p.setEncodeElements(new HashSet(Arrays.asList("Patient.name", "Bundle.entry"))); - p.setPrettyPrint(true); - String out = p.encodeResourceToString(bundle); - ourLog.info(out); - assertThat(out, not(containsString("total"))); - assertThat(out, (containsString("Patient"))); - assertThat(out, (containsString("name"))); - assertThat(out, not(containsString("address"))); - } - { - IParser p = ourCtx.newXmlParser(); - p.setEncodeElements(new HashSet(Arrays.asList("Patient.name"))); - p.setEncodeElementsAppliesToResourceTypes(new HashSet(Arrays.asList("Patient"))); - p.setPrettyPrint(true); - String out = p.encodeResourceToString(bundle); - ourLog.info(out); - assertThat(out, (containsString("total"))); - assertThat(out, (containsString("Patient"))); - assertThat(out, (containsString("name"))); - assertThat(out, not(containsString("address"))); - } - { - IParser p = ourCtx.newXmlParser(); - p.setEncodeElements(new HashSet(Arrays.asList("Patient"))); - p.setEncodeElementsAppliesToResourceTypes(new HashSet(Arrays.asList("Patient"))); - p.setPrettyPrint(true); - String out = p.encodeResourceToString(bundle); - ourLog.info(out); - assertThat(out, (containsString("total"))); - assertThat(out, (containsString("Patient"))); - assertThat(out, (containsString("name"))); - assertThat(out, (containsString("address"))); - } - - } - - @Test - public void testEncodeWithNarrative() { - Patient p = new Patient(); - p.addName().setFamily("Smith").addGiven("John"); - - ourCtx.setNarrativeGenerator(new DefaultThymeleafNarrativeGenerator()); - - String output = ourCtx.newXmlParser().encodeResourceToString(p); - ourLog.info(output); - - assertThat(output, containsString("
John SMITH ")); - } - - @Test - public void testMoreExtensions() throws Exception { - - Patient patient = new Patient(); - patient.addIdentifier().setUse(IdentifierUse.OFFICIAL).setSystem("urn:example").setValue("7000135"); - - Extension ext = new Extension(); - ext.setUrl("http://example.com/extensions#someext"); - ext.setValue(new DateTimeType("2011-01-02T11:13:15")); - - // Add the extension to the resource - patient.addExtension(ext); - // END SNIPPET: resourceExtension - - // START SNIPPET: resourceStringExtension - HumanName name = patient.addName(); - name.setFamily("Shmoe"); - StringType given = name.addGivenElement(); - given.setValue("Joe"); - Extension ext2 = new Extension().setUrl("http://examples.com#givenext").setValue(new StringType("given")); - given.addExtension(ext2); - - StringType given2 = name.addGivenElement(); - given2.setValue("Shmoe"); - Extension given2ext = new Extension().setUrl("http://examples.com#givenext_parent"); - given2.addExtension(given2ext); - Extension givenExtChild = new Extension(); - givenExtChild.setUrl("http://examples.com#givenext_child").setValue(new StringType("CHILD")); - given2ext.addExtension(givenExtChild); - // END SNIPPET: resourceStringExtension - - // START SNIPPET: subExtension - Extension parent = new Extension().setUrl("http://example.com#parent"); - patient.addExtension(parent); - - Extension child1 = new Extension().setUrl("http://example.com#child").setValue(new StringType("value1")); - parent.addExtension(child1); - - Extension child2 = new Extension().setUrl("http://example.com#child").setValue(new StringType("value1")); - parent.addExtension(child2); - // END SNIPPET: subExtension - - String output = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(patient); - ourLog.info(output); - - String enc = ourCtx.newXmlParser().encodeResourceToString(patient); - assertThat(enc, containsString("")); - assertThat(enc, containsString( - "")); - assertThat(enc, containsString("")); - assertThat(enc, containsString( - "")); - } - - @Test - public void testOmitResourceId() { - Patient p = new Patient(); - p.setId("123"); - p.addName().setFamily("ABC"); - - assertThat(ourCtx.newXmlParser().encodeResourceToString(p), stringContainsInOrder("123", "ABC")); - assertThat(ourCtx.newXmlParser().setOmitResourceId(true).encodeResourceToString(p), containsString("ABC")); - assertThat(ourCtx.newXmlParser().setOmitResourceId(true).encodeResourceToString(p), not(containsString("123"))); - } - - @Test - @Ignore - public void testParseAndEncodeBundle() throws Exception { - String content = IOUtils.toString(XmlParserDstu3Test.class.getResourceAsStream("/bundle-example.xml"), StandardCharsets.UTF_8); - - Bundle parsed = ourCtx.newXmlParser().parseResource(Bundle.class, content); - assertEquals("Bundle/example/_history/1", parsed.getIdElement().getValue()); - assertEquals("1", parsed.getMeta().getVersionId()); - assertEquals("1", parsed.getIdElement().getVersionIdPart()); - assertEquals(("2014-08-18T01:43:30Z"), parsed.getMeta().getLastUpdatedElement().getValueAsString()); - assertEquals("searchset", parsed.getType().toCode()); - assertEquals(3, parsed.getTotal()); - assertEquals("https://example.com/base/MedicationRequest?patient=347&searchId=ff15fd40-ff71-4b48-b366-09c706bed9d0&page=2", parsed.getLink("next").getUrl()); - assertEquals("https://example.com/base/MedicationRequest?patient=347&_include=MedicationRequest.medication", parsed.getLink("self").getUrl()); - - assertEquals(2, parsed.getEntry().size()); - assertEquals("http://foo?search", parsed.getEntry().get(0).getLink("search").getUrl()); - - assertEquals("http://example.com/base/MedicationRequest/3123/_history/1", parsed.getEntry().get(0).getLink("alternate").getUrl()); - MedicationRequest p = (MedicationRequest) parsed.getEntry().get(0).getResource(); - assertEquals("Patient/347", p.getSubject().getReference()); - assertEquals("2014-08-16T05:31:17Z", p.getMeta().getLastUpdatedElement().getValueAsString()); - assertEquals("http://example.com/base/MedicationRequest/3123/_history/1", p.getId()); - - Medication m = (Medication) parsed.getEntry().get(1).getResource(); - assertEquals("http://example.com/base/Medication/example", m.getId()); - assertSame(((Reference) p.getMedication()).getResource(), m); - - String reencoded = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(parsed); - ourLog.info(reencoded); - - Diff d = new Diff(new StringReader(content), new StringReader(reencoded)); - assertTrue(d.toString(), d.identical()); - - } - - @Test - @Ignore - public void testParseAndEncodeBundleNewStyle() throws Exception { - String content = IOUtils.toString(XmlParserDstu3Test.class.getResourceAsStream("/bundle-example.xml"), StandardCharsets.UTF_8); - - IParser newXmlParser = ourCtx.newXmlParser(); - Bundle parsed = newXmlParser.parseResource(Bundle.class, content); - assertEquals("Bundle/example/_history/1", parsed.getIdElement().getValue()); - assertEquals("1", parsed.getIdElement().getVersionIdPart()); - assertEquals("2014-08-18T01:43:30Z", parsed.getMeta().getLastUpdatedElement().getValueAsString()); - assertEquals("searchset", parsed.getType()); - assertEquals(3, parsed.getTotal()); - assertEquals("https://example.com/base/MedicationRequest?patient=347&searchId=ff15fd40-ff71-4b48-b366-09c706bed9d0&page=2", parsed.getLink().get(0).getUrlElement().getValueAsString()); - assertEquals("https://example.com/base/MedicationRequest?patient=347&_include=MedicationRequest.medication", parsed.getLink().get(1).getUrlElement().getValueAsString()); - - assertEquals(2, parsed.getEntry().size()); - assertEquals("alternate", parsed.getEntry().get(0).getLink().get(0).getRelation()); - assertEquals("http://example.com/base/MedicationRequest/3123/_history/1", parsed.getEntry().get(0).getLink().get(0).getUrl()); - assertEquals("http://foo?search", parsed.getEntry().get(0).getRequest().getUrlElement().getValueAsString()); - - MedicationRequest p = (MedicationRequest) parsed.getEntry().get(0).getResource(); - assertEquals("Patient/347", p.getSubject().getReference()); - assertEquals("2014-08-16T05:31:17Z", p.getMeta().getLastUpdatedElement().getValueAsString()); - assertEquals("http://example.com/base/MedicationRequest/3123/_history/1", p.getId()); - // assertEquals("3123", p.getId()); - - Medication m = (Medication) parsed.getEntry().get(1).getResource(); - assertEquals("http://example.com/base/Medication/example", m.getId()); - assertSame(((Reference) p.getMedication()).getResource(), m); - - String reencoded = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(parsed); - ourLog.info(reencoded); - - Diff d = new Diff(new StringReader(content), new StringReader(reencoded)); - assertTrue(d.toString(), d.identical()); - - } - - @Test - public void testParseAndEncodeComments() { - String input = "\n" + - " " + - " \n" + - " \n" + - " \n" + - "
\n" + - "\n" + - "

Patient Donald DUCK @ Acme Healthcare, Inc. MR = 654321

\n" + - "\n" + - "
\n" + - "
\n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " " + - " " + - "
"; - - Patient res = ourCtx.newXmlParser().parseResource(Patient.class, input); - res.getFormatCommentsPre(); - assertEquals("Patient/pat1", res.getId()); - assertEquals("654321", res.getIdentifier().get(0).getValue()); - assertEquals(true, res.getActive()); - - assertThat(res.getIdElement().getFormatCommentsPre(), contains("pre resource comment")); - assertThat(res.getIdentifier().get(0).getFormatCommentsPre(), contains("identifier comment 1", "identifier comment 2")); - assertThat(res.getIdentifier().get(0).getUseElement().getFormatCommentsPre(), contains("use comment 1", "use comment 2")); - assertThat(res.getActiveElement().getFormatCommentsPost(), contains("post resource comment")); - - String encoded = ourCtx.newJsonParser().setPrettyPrint(true).encodeResourceToString(res); - ourLog.info(encoded); - - assertThat(encoded, stringContainsInOrder( - "\"identifier\": [", - "{", - "\"fhir_comments\":", - "[", - "\"identifier comment 1\"", - ",", - "\"identifier comment 2\"", - "]", - "\"use\": \"usual\",", - "\"_use\": {", - "\"fhir_comments\":", - "[", - "\"use comment 1\"", - ",", - "\"use comment 2\"", - "]", - "},", - "\"type\"")); - - encoded = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(res); - ourLog.info(encoded); - - assertThat(encoded, stringContainsInOrder( - "", - "", - "", - "", - "
", - "

Patient Donald DUCK @ Acme Healthcare, Inc. MR = 654321

", - "
", - "
", - " \n", - " ", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "", - "
")); - - } - - @Test - public void testParseAndEncodeCommentsOnExtensions() { - - String input = "\n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - ""; - - Patient pat = ourCtx.newXmlParser().parseResource(Patient.class, input); - String output = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(pat); - ourLog.info(output); - - assertThat(output, stringContainsInOrder( - "", - " ", - " ", - " ", - " ", - " ", - " ", - " ", - " ", - " ", - " ", - " ", - " ", - " ", - " ", - "")); - - output = ourCtx.newJsonParser().setPrettyPrint(true).encodeResourceToString(pat); - ourLog.info(output); - - assertThat(output, stringContainsInOrder( - "{", - " \"resourceType\": \"Patient\",", - " \"id\": \"someid\",", - " \"_id\": {", - " \"fhir_comments\": [", - " \" comment 1 \"", - " ]", - " },", - " \"extension\": [", - " {", - " \"fhir_comments\": [", - " \" comment 2 \",", - " \" comment 7 \"", - " ],", - " \"url\": \"urn:patientext:att\",", - " \"valueAttachment\": {", - " \"fhir_comments\": [", - " \" comment 3 \",", - " \" comment 6 \"", - " ],", - " \"contentType\": \"aaaa\",", - " \"_contentType\": {", - " \"fhir_comments\": [", - " \" comment 4 \"", - " ]", - " },", - " \"data\": \"AAAA\",", - " \"_data\": {", - " \"fhir_comments\": [", - " \" comment 5 \"", - " ]", - " }", - " }", - " }", - " ]", - "}")); - - } - - @Test - public void testParseAndEncodeExtensionOnReference() { - - String input = "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - "" + - ""; - - DataElement de = ourCtx.newXmlParser().parseResource(DataElement.class, input); - String output = ourCtx.newXmlParser().encodeResourceToString(de).replace(" xmlns=\"http://hl7.org/fhir\"", ""); - - ElementDefinition elem = de.getElement().get(0); - ElementDefinitionBindingComponent b = elem.getBinding(); - // assertEquals("All codes representing the gender of a person.", b.getDescription()); - - Reference ref = (Reference) b.getValueSet(); - assertEquals("#2179414", ref.getReference()); - - assertEquals(2, ref.getExtension().size()); - Extension ext = ref.getExtension().get(0); - assertEquals("http://hl7.org/fhir/StructureDefinition/11179-permitted-value-valueset", ext.getUrl()); - assertEquals(Reference.class, ext.getValue().getClass()); - assertEquals("#2179414-permitted", ((Reference) ext.getValue()).getReference()); - assertEquals(ValueSet.class, ((Reference) ext.getValue()).getResource().getClass()); - - ext = ref.getExtension().get(1); - assertEquals("http://hl7.org/fhir/StructureDefinition/11179-permitted-value-conceptmap", ext.getUrl()); - assertEquals(Reference.class, ext.getValue().getClass()); - assertEquals("#2179414-cm", ((Reference) ext.getValue()).getReference()); - assertEquals(ConceptMap.class, ((Reference) ext.getValue()).getResource().getClass()); - - ourLog.info(ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(de)); - - assertThat(output, containsString("http://hl7.org/fhir/StructureDefinition/11179-permitted-value-valueset")); - - } - - @Test - public void testParseAndEncodeNestedExtensions() { - - String input = "\n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - ""; - - Patient p = ourCtx.newXmlParser().parseResource(Patient.class, input); - DateType bd = p.getBirthDateElement(); - assertEquals("2005-03-04", bd.getValueAsString()); - - List exts = bd.getExtensionsByUrl("http://my.fancy.extension.url"); - assertEquals(1, exts.size()); - Extension ext = exts.get(0); - assertEquals(null, ext.getValue()); - - exts = ext.getExtensionsByUrl("http://my.fancy.extension.url"); - assertEquals(1, exts.size()); - ext = exts.get(0); - assertEquals("myNestedValue", ((StringType) ext.getValue()).getValue()); - - String encoded = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(p); - ourLog.info(encoded); - - assertThat(encoded, stringContainsInOrder( - "", - "", - "", - "", - "", - "", - "", - "", - "")); - - } - - @Test - public void testParseBundleNewWithPlaceholderIds() { - - String input = "\n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - "\n"; - - Bundle parsed = ourCtx.newXmlParser().parseResource(Bundle.class, input); - assertEquals("urn:oid:0.1.2.3", parsed.getEntry().get(0).getResource().getIdElement().getValue()); - - } - - @Test - public void testParseBundleNewWithPlaceholderIdsInBase1() { - - String input = "\n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - "\n"; - - Bundle parsed = ourCtx.newXmlParser().parseResource(Bundle.class, input); - assertEquals("urn:oid:0.1.2.3", parsed.getEntry().get(0).getResource().getIdElement().getValue()); - } - - @Test - public void testParseBundleNewWithPlaceholderIdsInBase2() { - - String input = "\n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - "\n"; - - Bundle parsed = ourCtx.newXmlParser().parseResource(Bundle.class, input); - assertEquals("urn:uuid:0.1.2.3", parsed.getEntry().get(0).getResource().getIdElement().getValue()); - - input = "\n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - "\n"; - - parsed = ourCtx.newXmlParser().parseResource(Bundle.class, input); - assertEquals("urn:uuid:0.1.2.3", parsed.getEntry().get(0).getResource().getIdElement().getValue()); - - } - - @Test - public void testParseBundleOldStyleWithUnknownLinks() throws Exception { - - String bundle = "\n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - ""; - - Bundle b = (Bundle) ourCtx.newXmlParser().parseResource(bundle); - assertEquals(1, b.getEntry().size()); - - } - - @Test - public void testParseBundleOldWithPlaceholderIds() { - - String input = "\n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - "\n"; - - Bundle parsed = (Bundle) ourCtx.newXmlParser().parseResource(input); - assertEquals("urn:oid:0.1.2.3", parsed.getEntry().get(0).getResource().getId()); - - } - - @Test - public void testParseBundleWithBinary() { - // TODO: implement this test, make sure we handle ID and meta correctly in Binary - } - - /** - * See #191 - */ - @Test - public void testParseBundleWithLinksOfUnknownRelation() throws Exception { - String input = IOUtils.toString(XmlParserDstu3Test.class.getResourceAsStream("/bundle_orion.xml"), StandardCharsets.UTF_8); - Bundle parsed = ourCtx.newXmlParser().parseResource(Bundle.class, input); - - BundleLinkComponent link = parsed.getLink().get(0); - assertEquals("just trying add link", link.getRelation()); - assertEquals("blarion", link.getUrl()); - - BundleEntryComponent entry = parsed.getEntry().get(0); - link = entry.getLink().get(0); - assertEquals("orionhealth.edit", link.getRelation()); - assertEquals("Observation", link.getUrl()); - } - - @Test - public void testParseBundleWithResourceId() { - - String input = "" - + "" - + "" - + "" - + "\n"; - - Bundle bundle = ourCtx.newXmlParser().parseResource(Bundle.class, input); - assertEquals("http://localhost:58402/fhir/context/Patient/1/_history/3", bundle.getEntry().get(0).getResource().getIdElement().getValue()); - assertEquals("http://localhost:58402/fhir/context/Patient/1/_history/2", bundle.getEntry().get(1).getResource().getIdElement().getValue()); - assertEquals("http://localhost:58402/fhir/context/Patient/1/_history/1", bundle.getEntry().get(2).getResource().getIdElement().getValue()); - } - - /** - * see #144 and #146 - */ - @Test - @Ignore - public void testParseContained() { - - FhirContext c = FhirContext.forDstu3(); - IParser parser = c.newXmlParser().setPrettyPrint(true); - - Observation o = new Observation(); - o.getCode().setText("obs text"); - - Patient p = new Patient(); - p.addName().setFamily("patient family"); - o.getSubject().setResource(p); - - String enc = parser.encodeResourceToString(o); - ourLog.info(enc); - - assertThat(enc, stringContainsInOrder( - "", - "", - "", - "", - "", - "")); - - o = parser.parseResource(Observation.class, enc); - assertEquals("obs text", o.getCode().getText()); - - assertNotNull(o.getSubject().getResource()); - p = (Patient) o.getSubject().getResource(); - assertEquals("patient family", p.getName().get(0).getFamily()); - } - - /** - * Thanks to Alexander Kley! - */ - @Test - public void testParseContainedBinaryResource() { - byte[] bin = new byte[] { 0, 1, 2, 3, 4 }; - final Binary binary = new Binary(); - binary.setContentType("PatientConsent").setContent(bin); - - DocumentManifest manifest = new DocumentManifest(); - CodeableConcept cc = new CodeableConcept(); - cc.addCoding().setSystem("mySystem").setCode("PatientDocument"); - manifest.setType(cc); - manifest.setMasterIdentifier(new Identifier().setSystem("mySystem").setValue(UUID.randomUUID().toString())); - manifest.addContent().setP(new Reference(binary)); - manifest.setStatus(DocumentReferenceStatus.CURRENT); - - String encoded = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(manifest); - ourLog.info(encoded); - assertThat(encoded, StringContainsInOrder.stringContainsInOrder(Arrays.asList("contained>", ""))); - - DocumentManifest actual = ourCtx.newXmlParser().parseResource(DocumentManifest.class, encoded); - assertEquals(1, actual.getContained().size()); - assertEquals(1, actual.getContent().size()); - - /* - * If this fails, it's possibe the DocumentManifest structure is wrong: It should be - * - * @Child(name = "p", type = {Attachment.class, ValueSet.class}, order=1, min=1, max=1, modifier=false, summary=true) - */ - assertNotNull(((Reference) actual.getContent().get(0).getP()).getResource()); - } - - /** - * See #426 - */ - @Test - public void testParseExtensionWithIdType() { - - String input = "\n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - ""; - - Patient pt = ourCtx.newXmlParser().parseResource(Patient.class, input); - - List extList = pt.getExtensionsByUrl("http://aaa.ch/fhir/Patient#mangedcare"); - extList = extList.get(0).getExtensionsByUrl("http://aaa.ch/fhir/Patient#mangedcare-aaa-id"); - Extension ext = extList.get(0); - IdType value = (IdType) ext.getValue(); - assertEquals("mc1", value.getValueAsString()); - } - - /** - * See #426 - * - * Value type of FOO isn't a valid datatype - */ - @Test - public void testParseExtensionWithInvalidType() { - - String input = "\n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - ""; - - Patient pt = ourCtx.newXmlParser().parseResource(Patient.class, input); - - List extList = pt.getExtensionsByUrl("http://aaa.ch/fhir/Patient#mangedcare"); - extList = extList.get(0).getExtensionsByUrl("http://aaa.ch/fhir/Patient#mangedcare-aaa-id"); - Extension ext = extList.get(0); - IdType value = (IdType) ext.getValue(); - assertEquals(null, value); - } - - /** - * See #342 - */ - @Test(expected = DataFormatException.class) - public void testParseInvalid() { - ourCtx.newXmlParser().parseResource("FOO"); - } - - /** - * See #366 - */ - @Test() - public void testParseInvalidBoolean() { - - String resource = "\n" + - " \n" + - ""; - - IParser p = ourCtx.newXmlParser(); - - try { - p.parseResource(resource); - fail(); - } catch (DataFormatException e) { - assertEquals("DataFormatException at [[row,col {unknown-source}]: [2,4]]: Invalid attribute value \"1\": Invalid boolean string: '1'", e.getMessage()); - } - - LenientErrorHandler errorHandler = new LenientErrorHandler(); - assertEquals(true, errorHandler.isErrorOnInvalidValue()); - errorHandler.setErrorOnInvalidValue(false); - p.setParserErrorHandler(errorHandler); - } - - @Test - public void testParseInvalidTextualNumber() { - Observation obs = new Observation(); - obs.setValue(new Quantity().setValue(1234)); - String encoded = ourCtx.newJsonParser().setPrettyPrint(true).encodeResourceToString(obs); - encoded = encoded.replace("1234", "\"1234\""); - ourLog.info(encoded); - ourCtx.newJsonParser().parseResource(encoded); - } - - /** - * See #216 - */ - @Test - public void testParseMalformedIdentifierDstu2() { - - // This was changed from 0.5 to 1.0.0 - - String out = "\n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - ""; - - IParserErrorHandler errorHandler = mock(IParserErrorHandler.class); - - IParser p = ourCtx.newXmlParser(); - p.setParserErrorHandler(errorHandler); - - Patient patient = p.parseResource(Patient.class, out); - assertThat(patient.getIdentifier().get(0).getType().getCoding(), IsEmptyCollection.empty()); - - ArgumentCaptor capt = ArgumentCaptor.forClass(String.class); - verify(errorHandler, times(1)).unknownAttribute(any(IParseLocation.class), capt.capture()); - - assertEquals("value", capt.getValue()); - } - - @Test - public void testParseMetadata() throws Exception { - - String bundle = "\n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - ""; - - Bundle b = ourCtx.newXmlParser().parseResource(Bundle.class, bundle); - assertEquals(1, b.getEntry().size()); - - BundleEntryComponent entry = b.getEntry().get(0); - Patient pt = (Patient) entry.getResource(); - assertEquals("http://foo/fhirBase2/Patient/1/_history/2", pt.getIdElement().getValue()); - assertEquals("2012-01-02", pt.getBirthDateElement().getValueAsString()); - assertEquals("0.123", entry.getSearch().getScore().toString()); - assertEquals("match", entry.getSearch().getMode().toCode()); - assertEquals("POST", entry.getRequest().getMethod().toCode()); - assertEquals("http://foo/Patient?identifier=value", entry.getRequest().getUrl()); - assertEquals("2001-02-22T09:22:33-07:00", pt.getMeta().getLastUpdatedElement().getValueAsString()); - - IParser p = ourCtx.newXmlParser().setPrettyPrint(true); - String reEncoded = p.encodeResourceToString(b); - ourLog.info(reEncoded); - - Diff d = new Diff(new StringReader(bundle), new StringReader(reEncoded)); - assertTrue(d.toString(), d.identical()); - - } - - @Test - public void testParseMetaUpdatedDate() { - - String input = "\n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - ""; - - Bundle b = ourCtx.newXmlParser().parseResource(Bundle.class, input); - - InstantType updated = b.getMeta().getLastUpdatedElement(); - assertEquals("2015-06-22T15:48:57.554-04:00", updated.getValueAsString()); - - } - - // TODO: this should work - @Test - @Ignore - public void testParseNarrative() throws Exception { - - String htmlNoNs = "
AAABBBCCC
"; - String htmlNs = htmlNoNs.replace("
", "
"); - String res = "\n" + - " \n" + - " \n" + - " " + htmlNs + "\n" + - " \n" + - ""; - - Patient p = ourCtx.newXmlParser().parseResource(Patient.class, res); - assertEquals(htmlNs, p.getText().getDiv().getValueAsString()); - } - - @Test - public void testParseNestedExtensionsInvalid() { - - String input = "\n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - " \n" + - ""; - - try { - ourCtx.newXmlParser().parseResource(Patient.class, input); - fail(); - } catch (DataFormatException e) { - assertThat(e.getMessage(), containsString("Extension (URL='http://my.fancy.extension.url') must not have both a value and other contained extensions")); - } - } - - /** - * See #163 - */ - @Test - public void testParseResourceType() { - IParser xmlParser = ourCtx.newXmlParser().setPrettyPrint(true); - - // Patient - Patient patient = new Patient(); - String patientId = UUID.randomUUID().toString(); - patient.setId(new IdType("Patient", patientId)); - patient.addName().addGiven("John").setFamily("Smith"); - patient.setGender(AdministrativeGender.MALE); - patient.setBirthDateElement(new DateType("1987-04-16")); - - // Bundle - Bundle bundle = new Bundle(); - bundle.setType(BundleType.COLLECTION); - bundle.addEntry().setResource(patient); - - String bundleText = xmlParser.encodeResourceToString(bundle); - ourLog.info(bundleText); - - Bundle reincarnatedBundle = xmlParser.parseResource(Bundle.class, bundleText); - Patient reincarnatedPatient = (Patient) reincarnatedBundle.getEntry().get(0).getResource(); - - assertEquals("Patient", patient.getIdElement().getResourceType()); - assertEquals("Patient", reincarnatedPatient.getIdElement().getResourceType()); - } - - /** - * See #344 - */ - @Test - public void testParserIsCaseSensitive() { - Observation obs = new Observation(); - SampledData data = new SampledData(); - data.setData("1 2 3"); - data.setOrigin((SimpleQuantity) new SimpleQuantity().setValue(0L)); - data.setPeriod(1000L); - obs.setValue(data); - - IParser p = ourCtx.newXmlParser().setPrettyPrint(true).setParserErrorHandler(new StrictErrorHandler()); - String encoded = p.encodeResourceToString(obs); - ourLog.info(encoded); - - p.parseResource(encoded); - - try { - p.parseResource(encoded.replace("Observation", "observation")); - fail(); - } catch (DataFormatException e) { - assertEquals("DataFormatException at [[row,col {unknown-source}]: [1,1]]: Unknown resource type 'observation': Resource names are case sensitive, found similar name: 'Observation'", - e.getMessage()); - } - - try { - p.parseResource(encoded.replace("valueSampledData", "valueSampleddata")); - fail(); - } catch (DataFormatException e) { - assertEquals("DataFormatException at [[row,col {unknown-source}]: [2,4]]: Unknown element 'valueSampleddata' found during parse", e.getMessage()); - } - } - - @Test(expected = DataFormatException.class) - public void testParseWithInvalidLocalRef() throws IOException { - String string = IOUtils.toString(getClass().getResourceAsStream("/bundle_with_invalid_contained_ref.xml"), StandardCharsets.UTF_8); - - IParser parser = ourCtx.newXmlParser(); - parser.setParserErrorHandler(new StrictErrorHandler()); - parser.parseResource(Bundle.class, string); - } - - @Test() - public void testParseWithInvalidLocalRefLenient() throws IOException { - String string = IOUtils.toString(getClass().getResourceAsStream("/bundle_with_invalid_contained_ref.xml"), StandardCharsets.UTF_8); - - IParser parser = ourCtx.newXmlParser(); - parser.setParserErrorHandler(new LenientErrorHandler()); - parser.parseResource(Bundle.class, string); - } - - /** - * If a contained resource refers to a contained resource that comes after it, it should still be successfully - * woven together. - */ - @Test - public void testParseWovenContainedResources() throws IOException { - String string = IOUtils.toString(getClass().getResourceAsStream("/bundle_with_woven_obs.xml"), StandardCharsets.UTF_8); - - IParser parser = ourCtx.newXmlParser(); - parser.setParserErrorHandler(new StrictErrorHandler()); - org.hl7.fhir.dstu3.model.Bundle bundle = parser.parseResource(Bundle.class, string); - - DiagnosticReport resource = (DiagnosticReport) bundle.getEntry().get(0).getResource(); - Observation obs = (Observation) resource.getResult().get(1).getResource(); - assertEquals("#2", obs.getId()); - Reference performerFirstRep = obs.getPerformerFirstRep(); - Practitioner performer = (Practitioner) performerFirstRep.getResource(); - assertEquals("#3", performer.getId()); - } - - /** - * See #414 - */ - @Test - public void testParseXmlExtensionWithoutUrl() { - - String input = "\n" + - " \n" + - " \n" + - " \n" + - ""; - - IParser parser = ourCtx.newXmlParser(); - parser.setParserErrorHandler(new LenientErrorHandler()); - Patient parsed = (Patient) parser.parseResource(input); - assertEquals(1, parsed.getExtension().size()); - assertEquals(null, parsed.getExtension().get(0).getUrl()); - assertEquals("2011-01-02T11:13:15", parsed.getExtension().get(0).getValueAsPrimitive().getValueAsString()); - - try { - parser = ourCtx.newXmlParser(); - parser.setParserErrorHandler(new StrictErrorHandler()); - parser.parseResource(input); - fail(); - } catch (DataFormatException e) { - assertEquals("Resource is missing required element 'url' in parent element 'extension'", e.getCause().getMessage()); - } - - } - - /** - * See #414 - */ - @Test - public void testParseXmlModifierExtensionWithoutUrl() { - - String input = "\n" + - " \n" + - " \n" + - " \n" + - ""; - - IParser parser = ourCtx.newXmlParser(); - parser.setParserErrorHandler(new LenientErrorHandler()); - Patient parsed = (Patient) parser.parseResource(input); - assertEquals(1, parsed.getModifierExtension().size()); - assertEquals(null, parsed.getModifierExtension().get(0).getUrl()); - assertEquals("2011-01-02T11:13:15", parsed.getModifierExtension().get(0).getValueAsPrimitive().getValueAsString()); - - try { - parser = ourCtx.newXmlParser(); - parser.setParserErrorHandler(new StrictErrorHandler()); - parser.parseResource(input); - fail(); - } catch (DataFormatException e) { - assertEquals("Resource is missing required element 'url' in parent element 'modifierExtension'", e.getCause().getMessage()); - } - - } - - /** - * See #339 - * - * https://www.owasp.org/index.php/XML_External_Entity_(XXE)_Processing - */ - @Test - public void testXxe() { - - String input = "" + - "" + - "]>" + - "" + - "" + - "
TEXT &xxe; TEXT
" + - "
" + - "
" + - "" + - "
" + - "
"; - - ourLog.info(input); - - try { - ourCtx.newXmlParser().parseResource(Patient.class, input); - fail(); - } catch (DataFormatException e) { - assertThat(e.toString(), containsString("Undeclared general entity")); - } - - } - - /** - * Test for the url generated based on the server config - */ - @Test - public void testGeneratedUrls() { - final IParser xmlParser = ourCtx.newXmlParser().setPrettyPrint(true); - xmlParser.setServerBaseUrl("http://myserver.com"); - - final CustomPatientDstu3 patient = new CustomPatientDstu3(); - patient.setHomeless(new BooleanType(true)); - - final String parsedPatient = xmlParser.encodeResourceToString(patient); - - assertTrue(parsedPatient.contains("")); - assertTrue(parsedPatient.contains("")); - } - - /** - * Test for the url generated based on the server config - */ - @Test - public void testCustomUrlExtension() { - final String expected = ""; - - final MyPatientWithCustomUrlExtension patient = new MyPatientWithCustomUrlExtension(); - patient.setPetName(new StringType("myName")); - - final IParser xmlParser = ourCtx.newXmlParser(); - xmlParser.setServerBaseUrl("http://www.example.com"); - - final String parsedPatient = xmlParser.encodeResourceToString(patient); - System.out.println(parsedPatient); - assertEquals(expected, parsedPatient); - - // Parse with string - MyPatientWithCustomUrlExtension newPatient = xmlParser.parseResource(MyPatientWithCustomUrlExtension.class, parsedPatient); - assertEquals("myName", newPatient.getPetName().getValue()); - - // Parse with stream - newPatient = xmlParser.parseResource(MyPatientWithCustomUrlExtension.class, new StringReader(parsedPatient)); - assertEquals("myName", newPatient.getPetName().getValue()); - - // Check no NPE if base server not configure - newPatient = ourCtx.newXmlParser().parseResource(MyPatientWithCustomUrlExtension.class, new StringReader(parsedPatient)); - assertNull("myName", newPatient.getPetName().getValue()); - assertEquals("myName", ((StringType) newPatient.getExtensionsByUrl("http://www.example.com/petname").get(0).getValue()).getValue()); - } - - @Test - public void testCustomUrlExtensioninBundle() { - final String expected = ""; - - final MyPatientWithCustomUrlExtension patient = new MyPatientWithCustomUrlExtension(); - patient.setPetName(new StringType("myName")); - - final Bundle bundle = new Bundle(); - final BundleEntryComponent entry = new BundleEntryComponent(); - entry.setResource(patient); - bundle.addEntry(entry); - - final IParser xmlParser = ourCtx.newXmlParser(); - xmlParser.setServerBaseUrl("http://www.example.com"); - - final String parsedBundle = xmlParser.encodeResourceToString(bundle); - System.out.println(parsedBundle); - assertEquals(expected, parsedBundle); - - // Parse with string - Bundle newBundle = xmlParser.parseResource(Bundle.class, parsedBundle); - assertNotNull(newBundle); - assertEquals(1, newBundle.getEntry().size()); - Patient newPatient = (Patient) newBundle.getEntry().get(0).getResource(); - assertEquals("myName", ((StringType) newPatient.getExtensionsByUrl("http://www.example.com/petname").get(0).getValue()).getValue()); - - // Parse with stream - newBundle = xmlParser.parseResource(Bundle.class, new StringReader(parsedBundle)); - assertNotNull(newBundle); - assertEquals(1, newBundle.getEntry().size()); - newPatient = (Patient) newBundle.getEntry().get(0).getResource(); - assertEquals("myName", ((StringType) newPatient.getExtensionsByUrl("http://www.example.com/petname").get(0).getValue()).getValue()); - - } - - @AfterClass - public static void afterClassClearContext() { - TestUtil.clearAllStaticFieldsForUnitTest(); - } - - @BeforeClass - public static void beforeClass() { - XMLUnit.setIgnoreAttributeOrder(true); - XMLUnit.setIgnoreComments(true); - XMLUnit.setIgnoreWhitespace(true); - } - - public static void main(String[] args) { - IGenericClient c = ourCtx.newRestfulGenericClient("http://fhir-dev.healthintersections.com.au/open"); - // c.registerInterceptor(new LoggingInterceptor(true)); - c.read().resource("Patient").withId("324").execute(); - } - - @ResourceDef(name = "Patient") - public static class TestPatientFor327 extends Patient { - - private static final long serialVersionUID = 1L; - - @Child(name = "testCondition") - @ca.uhn.fhir.model.api.annotation.Extension(url = "testCondition", definedLocally = true, isModifier = false) - private List testConditions = null; - - public List getConditions() { - return this.testConditions; - } - - public void setCondition(List ref) { - this.testConditions = ref; - } - } + @Test + @Ignore + public void testParseAndEncodeBundle() throws Exception { + String content = IOUtils.toString(XmlParserDstu3Test.class.getResourceAsStream("/bundle-example.xml"), StandardCharsets.UTF_8); + + Bundle parsed = ourCtx.newXmlParser().parseResource(Bundle.class, content); + assertEquals("Bundle/example/_history/1", parsed.getIdElement().getValue()); + assertEquals("1", parsed.getMeta().getVersionId()); + assertEquals("1", parsed.getIdElement().getVersionIdPart()); + assertEquals(("2014-08-18T01:43:30Z"), parsed.getMeta().getLastUpdatedElement().getValueAsString()); + assertEquals("searchset", parsed.getType().toCode()); + assertEquals(3, parsed.getTotal()); + assertEquals("https://example.com/base/MedicationRequest?patient=347&searchId=ff15fd40-ff71-4b48-b366-09c706bed9d0&page=2", parsed.getLink("next").getUrl()); + assertEquals("https://example.com/base/MedicationRequest?patient=347&_include=MedicationRequest.medication", parsed.getLink("self").getUrl()); + + assertEquals(2, parsed.getEntry().size()); + assertEquals("http://foo?search", parsed.getEntry().get(0).getLink("search").getUrl()); + + assertEquals("http://example.com/base/MedicationRequest/3123/_history/1", parsed.getEntry().get(0).getLink("alternate").getUrl()); + MedicationRequest p = (MedicationRequest) parsed.getEntry().get(0).getResource(); + assertEquals("Patient/347", p.getSubject().getReference()); + assertEquals("2014-08-16T05:31:17Z", p.getMeta().getLastUpdatedElement().getValueAsString()); + assertEquals("http://example.com/base/MedicationRequest/3123/_history/1", p.getId()); + + Medication m = (Medication) parsed.getEntry().get(1).getResource(); + assertEquals("http://example.com/base/Medication/example", m.getId()); + assertSame(((Reference) p.getMedication()).getResource(), m); + + String reencoded = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(parsed); + ourLog.info(reencoded); + + Diff d = new Diff(new StringReader(content), new StringReader(reencoded)); + assertTrue(d.toString(), d.identical()); + + } + + @Test + @Ignore + public void testParseAndEncodeBundleNewStyle() throws Exception { + String content = IOUtils.toString(XmlParserDstu3Test.class.getResourceAsStream("/bundle-example.xml"), StandardCharsets.UTF_8); + + IParser newXmlParser = ourCtx.newXmlParser(); + Bundle parsed = newXmlParser.parseResource(Bundle.class, content); + assertEquals("Bundle/example/_history/1", parsed.getIdElement().getValue()); + assertEquals("1", parsed.getIdElement().getVersionIdPart()); + assertEquals("2014-08-18T01:43:30Z", parsed.getMeta().getLastUpdatedElement().getValueAsString()); + assertEquals("searchset", parsed.getType()); + assertEquals(3, parsed.getTotal()); + assertEquals("https://example.com/base/MedicationRequest?patient=347&searchId=ff15fd40-ff71-4b48-b366-09c706bed9d0&page=2", parsed.getLink().get(0).getUrlElement().getValueAsString()); + assertEquals("https://example.com/base/MedicationRequest?patient=347&_include=MedicationRequest.medication", parsed.getLink().get(1).getUrlElement().getValueAsString()); + + assertEquals(2, parsed.getEntry().size()); + assertEquals("alternate", parsed.getEntry().get(0).getLink().get(0).getRelation()); + assertEquals("http://example.com/base/MedicationRequest/3123/_history/1", parsed.getEntry().get(0).getLink().get(0).getUrl()); + assertEquals("http://foo?search", parsed.getEntry().get(0).getRequest().getUrlElement().getValueAsString()); + + MedicationRequest p = (MedicationRequest) parsed.getEntry().get(0).getResource(); + assertEquals("Patient/347", p.getSubject().getReference()); + assertEquals("2014-08-16T05:31:17Z", p.getMeta().getLastUpdatedElement().getValueAsString()); + assertEquals("http://example.com/base/MedicationRequest/3123/_history/1", p.getId()); + // assertEquals("3123", p.getId()); + + Medication m = (Medication) parsed.getEntry().get(1).getResource(); + assertEquals("http://example.com/base/Medication/example", m.getId()); + assertSame(((Reference) p.getMedication()).getResource(), m); + + String reencoded = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(parsed); + ourLog.info(reencoded); + + Diff d = new Diff(new StringReader(content), new StringReader(reencoded)); + assertTrue(d.toString(), d.identical()); + + } + + @Test + public void testParseAndEncodeComments() { + String input = "\n" + + " " + + " \n" + + " \n" + + " \n" + + "
\n" + + "\n" + + "

Patient Donald DUCK @ Acme Healthcare, Inc. MR = 654321

\n" + + "\n" + + "
\n" + + "
\n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " " + + " " + + "
"; + + Patient res = ourCtx.newXmlParser().parseResource(Patient.class, input); + res.getFormatCommentsPre(); + assertEquals("Patient/pat1", res.getId()); + assertEquals("654321", res.getIdentifier().get(0).getValue()); + assertEquals(true, res.getActive()); + + assertThat(res.getIdElement().getFormatCommentsPre(), contains("pre resource comment")); + assertThat(res.getIdentifier().get(0).getFormatCommentsPre(), contains("identifier comment 1", "identifier comment 2")); + assertThat(res.getIdentifier().get(0).getUseElement().getFormatCommentsPre(), contains("use comment 1", "use comment 2")); + assertThat(res.getActiveElement().getFormatCommentsPost(), contains("post resource comment")); + + String encoded = ourCtx.newJsonParser().setPrettyPrint(true).encodeResourceToString(res); + ourLog.info(encoded); + + assertThat(encoded, stringContainsInOrder( + "\"identifier\": [", + "{", + "\"fhir_comments\":", + "[", + "\"identifier comment 1\"", + ",", + "\"identifier comment 2\"", + "]", + "\"use\": \"usual\",", + "\"_use\": {", + "\"fhir_comments\":", + "[", + "\"use comment 1\"", + ",", + "\"use comment 2\"", + "]", + "},", + "\"type\"")); + + encoded = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(res); + ourLog.info(encoded); + + assertThat(encoded, stringContainsInOrder( + "", + "", + "", + "", + "
", + "

Patient Donald DUCK @ Acme Healthcare, Inc. MR = 654321

", + "
", + "
", + " \n", + " ", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "
")); + + } + + @Test + public void testParseAndEncodeCommentsOnExtensions() { + + String input = "\n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + ""; + + Patient pat = ourCtx.newXmlParser().parseResource(Patient.class, input); + String output = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(pat); + ourLog.info(output); + + assertThat(output, stringContainsInOrder( + "", + " ", + " ", + " ", + " ", + " ", + " ", + " ", + " ", + " ", + " ", + " ", + " ", + " ", + " ", + "")); + + output = ourCtx.newJsonParser().setPrettyPrint(true).encodeResourceToString(pat); + ourLog.info(output); + + assertThat(output, stringContainsInOrder( + "{", + " \"resourceType\": \"Patient\",", + " \"id\": \"someid\",", + " \"_id\": {", + " \"fhir_comments\": [", + " \" comment 1 \"", + " ]", + " },", + " \"extension\": [", + " {", + " \"fhir_comments\": [", + " \" comment 2 \",", + " \" comment 7 \"", + " ],", + " \"url\": \"urn:patientext:att\",", + " \"valueAttachment\": {", + " \"fhir_comments\": [", + " \" comment 3 \",", + " \" comment 6 \"", + " ],", + " \"contentType\": \"aaaa\",", + " \"_contentType\": {", + " \"fhir_comments\": [", + " \" comment 4 \"", + " ]", + " },", + " \"data\": \"AAAA\",", + " \"_data\": {", + " \"fhir_comments\": [", + " \" comment 5 \"", + " ]", + " }", + " }", + " }", + " ]", + "}")); + + } + + @Test + public void testParseAndEncodeExtensionOnReference() { + + String input = "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + "" + + ""; + + DataElement de = ourCtx.newXmlParser().parseResource(DataElement.class, input); + String output = ourCtx.newXmlParser().encodeResourceToString(de).replace(" xmlns=\"http://hl7.org/fhir\"", ""); + + ElementDefinition elem = de.getElement().get(0); + ElementDefinitionBindingComponent b = elem.getBinding(); + // assertEquals("All codes representing the gender of a person.", b.getDescription()); + + Reference ref = (Reference) b.getValueSet(); + assertEquals("#2179414", ref.getReference()); + + assertEquals(2, ref.getExtension().size()); + Extension ext = ref.getExtension().get(0); + assertEquals("http://hl7.org/fhir/StructureDefinition/11179-permitted-value-valueset", ext.getUrl()); + assertEquals(Reference.class, ext.getValue().getClass()); + assertEquals("#2179414-permitted", ((Reference) ext.getValue()).getReference()); + assertEquals(ValueSet.class, ((Reference) ext.getValue()).getResource().getClass()); + + ext = ref.getExtension().get(1); + assertEquals("http://hl7.org/fhir/StructureDefinition/11179-permitted-value-conceptmap", ext.getUrl()); + assertEquals(Reference.class, ext.getValue().getClass()); + assertEquals("#2179414-cm", ((Reference) ext.getValue()).getReference()); + assertEquals(ConceptMap.class, ((Reference) ext.getValue()).getResource().getClass()); + + ourLog.info(ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(de)); + + assertThat(output, containsString("http://hl7.org/fhir/StructureDefinition/11179-permitted-value-valueset")); + + } + + @Test + public void testParseAndEncodeNestedExtensions() { + + String input = "\n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + ""; + + Patient p = ourCtx.newXmlParser().parseResource(Patient.class, input); + DateType bd = p.getBirthDateElement(); + assertEquals("2005-03-04", bd.getValueAsString()); + + List exts = bd.getExtensionsByUrl("http://my.fancy.extension.url"); + assertEquals(1, exts.size()); + Extension ext = exts.get(0); + assertEquals(null, ext.getValue()); + + exts = ext.getExtensionsByUrl("http://my.fancy.extension.url"); + assertEquals(1, exts.size()); + ext = exts.get(0); + assertEquals("myNestedValue", ((StringType) ext.getValue()).getValue()); + + String encoded = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(p); + ourLog.info(encoded); + + assertThat(encoded, stringContainsInOrder( + "", + "", + "", + "", + "", + "", + "", + "", + "")); + + } + + @Test + public void testParseBundleNewWithPlaceholderIds() { + + String input = "\n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + "\n"; + + Bundle parsed = ourCtx.newXmlParser().parseResource(Bundle.class, input); + assertEquals("urn:oid:0.1.2.3", parsed.getEntry().get(0).getResource().getIdElement().getValue()); + + } + + @Test + public void testParseBundleNewWithPlaceholderIdsInBase1() { + + String input = "\n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + "\n"; + + Bundle parsed = ourCtx.newXmlParser().parseResource(Bundle.class, input); + assertEquals("urn:oid:0.1.2.3", parsed.getEntry().get(0).getResource().getIdElement().getValue()); + } + + @Test + public void testParseBundleNewWithPlaceholderIdsInBase2() { + + String input = "\n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + "\n"; + + Bundle parsed = ourCtx.newXmlParser().parseResource(Bundle.class, input); + assertEquals("urn:uuid:0.1.2.3", parsed.getEntry().get(0).getResource().getIdElement().getValue()); + + input = "\n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + "\n"; + + parsed = ourCtx.newXmlParser().parseResource(Bundle.class, input); + assertEquals("urn:uuid:0.1.2.3", parsed.getEntry().get(0).getResource().getIdElement().getValue()); + + } + + @Test + public void testParseBundleOldStyleWithUnknownLinks() throws Exception { + + String bundle = "\n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + ""; + + Bundle b = (Bundle) ourCtx.newXmlParser().parseResource(bundle); + assertEquals(1, b.getEntry().size()); + + } + + @Test + public void testParseBundleOldWithPlaceholderIds() { + + String input = "\n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + "\n"; + + Bundle parsed = (Bundle) ourCtx.newXmlParser().parseResource(input); + assertEquals("urn:oid:0.1.2.3", parsed.getEntry().get(0).getResource().getId()); + + } + + @Test + public void testParseBundleWithBinary() { + // TODO: implement this test, make sure we handle ID and meta correctly in Binary + } + + /** + * See #191 + */ + @Test + public void testParseBundleWithLinksOfUnknownRelation() throws Exception { + String input = IOUtils.toString(XmlParserDstu3Test.class.getResourceAsStream("/bundle_orion.xml"), StandardCharsets.UTF_8); + Bundle parsed = ourCtx.newXmlParser().parseResource(Bundle.class, input); + + BundleLinkComponent link = parsed.getLink().get(0); + assertEquals("just trying add link", link.getRelation()); + assertEquals("blarion", link.getUrl()); + + BundleEntryComponent entry = parsed.getEntry().get(0); + link = entry.getLink().get(0); + assertEquals("orionhealth.edit", link.getRelation()); + assertEquals("Observation", link.getUrl()); + } + + @Test + public void testParseBundleWithResourceId() { + + String input = "" + + "" + + "" + + "" + + "\n"; + + Bundle bundle = ourCtx.newXmlParser().parseResource(Bundle.class, input); + assertEquals("http://localhost:58402/fhir/context/Patient/1/_history/3", bundle.getEntry().get(0).getResource().getIdElement().getValue()); + assertEquals("http://localhost:58402/fhir/context/Patient/1/_history/2", bundle.getEntry().get(1).getResource().getIdElement().getValue()); + assertEquals("http://localhost:58402/fhir/context/Patient/1/_history/1", bundle.getEntry().get(2).getResource().getIdElement().getValue()); + } + + /** + * see #144 and #146 + */ + @Test + @Ignore + public void testParseContained() { + + FhirContext c = FhirContext.forDstu3(); + IParser parser = c.newXmlParser().setPrettyPrint(true); + + Observation o = new Observation(); + o.getCode().setText("obs text"); + + Patient p = new Patient(); + p.addName().setFamily("patient family"); + o.getSubject().setResource(p); + + String enc = parser.encodeResourceToString(o); + ourLog.info(enc); + + assertThat(enc, stringContainsInOrder( + "", + "", + "", + "", + "", + "")); + + o = parser.parseResource(Observation.class, enc); + assertEquals("obs text", o.getCode().getText()); + + assertNotNull(o.getSubject().getResource()); + p = (Patient) o.getSubject().getResource(); + assertEquals("patient family", p.getName().get(0).getFamily()); + } + + /** + * Thanks to Alexander Kley! + */ + @Test + public void testParseContainedBinaryResource() { + byte[] bin = new byte[] { 0, 1, 2, 3, 4 }; + final Binary binary = new Binary(); + binary.setContentType("PatientConsent").setContent(bin); + + DocumentManifest manifest = new DocumentManifest(); + CodeableConcept cc = new CodeableConcept(); + cc.addCoding().setSystem("mySystem").setCode("PatientDocument"); + manifest.setType(cc); + manifest.setMasterIdentifier(new Identifier().setSystem("mySystem").setValue(UUID.randomUUID().toString())); + manifest.addContent().setP(new Reference(binary)); + manifest.setStatus(DocumentReferenceStatus.CURRENT); + + String encoded = ourCtx.newXmlParser().setPrettyPrint(true).encodeResourceToString(manifest); + ourLog.info(encoded); + assertThat(encoded, StringContainsInOrder.stringContainsInOrder(Arrays.asList("contained>", ""))); + + DocumentManifest actual = ourCtx.newXmlParser().parseResource(DocumentManifest.class, encoded); + assertEquals(1, actual.getContained().size()); + assertEquals(1, actual.getContent().size()); + + /* + * If this fails, it's possibe the DocumentManifest structure is wrong: It should be + * + * @Child(name = "p", type = {Attachment.class, ValueSet.class}, order=1, min=1, max=1, modifier=false, summary=true) + */ + assertNotNull(((Reference) actual.getContent().get(0).getP()).getResource()); + } + + /** + * See #426 + */ + @Test + public void testParseExtensionWithIdType() { + + String input = "\n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + ""; + + Patient pt = ourCtx.newXmlParser().parseResource(Patient.class, input); + + List extList = pt.getExtensionsByUrl("http://aaa.ch/fhir/Patient#mangedcare"); + extList = extList.get(0).getExtensionsByUrl("http://aaa.ch/fhir/Patient#mangedcare-aaa-id"); + Extension ext = extList.get(0); + IdType value = (IdType) ext.getValue(); + assertEquals("mc1", value.getValueAsString()); + } + + /** + * See #426 + * + * Value type of FOO isn't a valid datatype + */ + @Test + public void testParseExtensionWithInvalidType() { + + String input = "\n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + ""; + + Patient pt = ourCtx.newXmlParser().parseResource(Patient.class, input); + + List extList = pt.getExtensionsByUrl("http://aaa.ch/fhir/Patient#mangedcare"); + extList = extList.get(0).getExtensionsByUrl("http://aaa.ch/fhir/Patient#mangedcare-aaa-id"); + Extension ext = extList.get(0); + IdType value = (IdType) ext.getValue(); + assertEquals(null, value); + } + + /** + * See #342 + */ + @Test(expected = DataFormatException.class) + public void testParseInvalid() { + ourCtx.newXmlParser().parseResource("FOO"); + } + + /** + * See #366 + */ + @Test() + public void testParseInvalidBoolean() { + + String resource = "\n" + + " \n" + + ""; + + IParser p = ourCtx.newXmlParser(); + + try { + p.parseResource(resource); + fail(); + } catch (DataFormatException e) { + assertEquals("DataFormatException at [[row,col {unknown-source}]: [2,4]]: Invalid attribute value \"1\": Invalid boolean string: '1'", e.getMessage()); + } + + LenientErrorHandler errorHandler = new LenientErrorHandler(); + assertEquals(true, errorHandler.isErrorOnInvalidValue()); + errorHandler.setErrorOnInvalidValue(false); + p.setParserErrorHandler(errorHandler); + } + + @Test + public void testParseInvalidTextualNumber() { + Observation obs = new Observation(); + obs.setValue(new Quantity().setValue(1234)); + String encoded = ourCtx.newJsonParser().setPrettyPrint(true).encodeResourceToString(obs); + encoded = encoded.replace("1234", "\"1234\""); + ourLog.info(encoded); + ourCtx.newJsonParser().parseResource(encoded); + } + + /** + * See #216 + */ + @Test + public void testParseMalformedIdentifierDstu2() { + + // This was changed from 0.5 to 1.0.0 + + String out = "\n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + ""; + + IParserErrorHandler errorHandler = mock(IParserErrorHandler.class); + + IParser p = ourCtx.newXmlParser(); + p.setParserErrorHandler(errorHandler); + + Patient patient = p.parseResource(Patient.class, out); + assertThat(patient.getIdentifier().get(0).getType().getCoding(), IsEmptyCollection.empty()); + + ArgumentCaptor capt = ArgumentCaptor.forClass(String.class); + verify(errorHandler, times(1)).unknownAttribute(any(IParseLocation.class), capt.capture()); + + assertEquals("value", capt.getValue()); + } + + @Test + public void testParseMetadata() throws Exception { + + String bundle = "\n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + ""; + + Bundle b = ourCtx.newXmlParser().parseResource(Bundle.class, bundle); + assertEquals(1, b.getEntry().size()); + + BundleEntryComponent entry = b.getEntry().get(0); + Patient pt = (Patient) entry.getResource(); + assertEquals("http://foo/fhirBase2/Patient/1/_history/2", pt.getIdElement().getValue()); + assertEquals("2012-01-02", pt.getBirthDateElement().getValueAsString()); + assertEquals("0.123", entry.getSearch().getScore().toString()); + assertEquals("match", entry.getSearch().getMode().toCode()); + assertEquals("POST", entry.getRequest().getMethod().toCode()); + assertEquals("http://foo/Patient?identifier=value", entry.getRequest().getUrl()); + assertEquals("2001-02-22T09:22:33-07:00", pt.getMeta().getLastUpdatedElement().getValueAsString()); + + IParser p = ourCtx.newXmlParser().setPrettyPrint(true); + String reEncoded = p.encodeResourceToString(b); + ourLog.info(reEncoded); + + Diff d = new Diff(new StringReader(bundle), new StringReader(reEncoded)); + assertTrue(d.toString(), d.identical()); + + } + + @Test + public void testParseMetaUpdatedDate() { + + String input = "\n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + ""; + + Bundle b = ourCtx.newXmlParser().parseResource(Bundle.class, input); + + InstantType updated = b.getMeta().getLastUpdatedElement(); + assertEquals("2015-06-22T15:48:57.554-04:00", updated.getValueAsString()); + + } + + // TODO: this should work + @Test + @Ignore + public void testParseNarrative() throws Exception { + + String htmlNoNs = "
AAABBBCCC
"; + String htmlNs = htmlNoNs.replace("
", "
"); + String res = "\n" + + " \n" + + " \n" + + " " + htmlNs + "\n" + + " \n" + + ""; + + Patient p = ourCtx.newXmlParser().parseResource(Patient.class, res); + assertEquals(htmlNs, p.getText().getDiv().getValueAsString()); + } + + @Test + public void testParseNestedExtensionsInvalid() { + + String input = "\n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + " \n" + + ""; + + try { + ourCtx.newXmlParser().parseResource(Patient.class, input); + fail(); + } catch (DataFormatException e) { + assertThat(e.getMessage(), containsString("Extension (URL='http://my.fancy.extension.url') must not have both a value and other contained extensions")); + } + } + + /** + * See #163 + */ + @Test + public void testParseResourceType() { + IParser xmlParser = ourCtx.newXmlParser().setPrettyPrint(true); + + // Patient + Patient patient = new Patient(); + String patientId = UUID.randomUUID().toString(); + patient.setId(new IdType("Patient", patientId)); + patient.addName().addGiven("John").setFamily("Smith"); + patient.setGender(AdministrativeGender.MALE); + patient.setBirthDateElement(new DateType("1987-04-16")); + + // Bundle + Bundle bundle = new Bundle(); + bundle.setType(BundleType.COLLECTION); + bundle.addEntry().setResource(patient); + + String bundleText = xmlParser.encodeResourceToString(bundle); + ourLog.info(bundleText); + + Bundle reincarnatedBundle = xmlParser.parseResource(Bundle.class, bundleText); + Patient reincarnatedPatient = (Patient) reincarnatedBundle.getEntry().get(0).getResource(); + + assertEquals("Patient", patient.getIdElement().getResourceType()); + assertEquals("Patient", reincarnatedPatient.getIdElement().getResourceType()); + } + + /** + * See #344 + */ + @Test + public void testParserIsCaseSensitive() { + Observation obs = new Observation(); + SampledData data = new SampledData(); + data.setData("1 2 3"); + data.setOrigin((SimpleQuantity) new SimpleQuantity().setValue(0L)); + data.setPeriod(1000L); + obs.setValue(data); + + IParser p = ourCtx.newXmlParser().setPrettyPrint(true).setParserErrorHandler(new StrictErrorHandler()); + String encoded = p.encodeResourceToString(obs); + ourLog.info(encoded); + + p.parseResource(encoded); + + try { + p.parseResource(encoded.replace("Observation", "observation")); + fail(); + } catch (DataFormatException e) { + assertEquals("DataFormatException at [[row,col {unknown-source}]: [1,1]]: Unknown resource type 'observation': Resource names are case sensitive, found similar name: 'Observation'", + e.getMessage()); + } + + try { + p.parseResource(encoded.replace("valueSampledData", "valueSampleddata")); + fail(); + } catch (DataFormatException e) { + assertEquals("DataFormatException at [[row,col {unknown-source}]: [2,4]]: Unknown element 'valueSampleddata' found during parse", e.getMessage()); + } + } + + @Test(expected = DataFormatException.class) + public void testParseWithInvalidLocalRef() throws IOException { + String string = IOUtils.toString(getClass().getResourceAsStream("/bundle_with_invalid_contained_ref.xml"), StandardCharsets.UTF_8); + + IParser parser = ourCtx.newXmlParser(); + parser.setParserErrorHandler(new StrictErrorHandler()); + parser.parseResource(Bundle.class, string); + } + + @Test() + public void testParseWithInvalidLocalRefLenient() throws IOException { + String string = IOUtils.toString(getClass().getResourceAsStream("/bundle_with_invalid_contained_ref.xml"), StandardCharsets.UTF_8); + + IParser parser = ourCtx.newXmlParser(); + parser.setParserErrorHandler(new LenientErrorHandler()); + parser.parseResource(Bundle.class, string); + } + + /** + * If a contained resource refers to a contained resource that comes after it, it should still be successfully + * woven together. + */ + @Test + public void testParseWovenContainedResources() throws IOException { + String string = IOUtils.toString(getClass().getResourceAsStream("/bundle_with_woven_obs.xml"), StandardCharsets.UTF_8); + + IParser parser = ourCtx.newXmlParser(); + parser.setParserErrorHandler(new StrictErrorHandler()); + org.hl7.fhir.dstu3.model.Bundle bundle = parser.parseResource(Bundle.class, string); + + DiagnosticReport resource = (DiagnosticReport) bundle.getEntry().get(0).getResource(); + Observation obs = (Observation) resource.getResult().get(1).getResource(); + assertEquals("#2", obs.getId()); + Reference performerFirstRep = obs.getPerformerFirstRep(); + Practitioner performer = (Practitioner) performerFirstRep.getResource(); + assertEquals("#3", performer.getId()); + } + + /** + * See #414 + */ + @Test + public void testParseXmlExtensionWithoutUrl() { + + String input = "\n" + + " \n" + + " \n" + + " \n" + + ""; + + IParser parser = ourCtx.newXmlParser(); + parser.setParserErrorHandler(new LenientErrorHandler()); + Patient parsed = (Patient) parser.parseResource(input); + assertEquals(1, parsed.getExtension().size()); + assertEquals(null, parsed.getExtension().get(0).getUrl()); + assertEquals("2011-01-02T11:13:15", parsed.getExtension().get(0).getValueAsPrimitive().getValueAsString()); + + try { + parser = ourCtx.newXmlParser(); + parser.setParserErrorHandler(new StrictErrorHandler()); + parser.parseResource(input); + fail(); + } catch (DataFormatException e) { + assertEquals("Resource is missing required element 'url' in parent element 'extension'", e.getCause().getMessage()); + } + + } + + /** + * See #414 + */ + @Test + public void testParseXmlModifierExtensionWithoutUrl() { + + String input = "\n" + + " \n" + + " \n" + + " \n" + + ""; + + IParser parser = ourCtx.newXmlParser(); + parser.setParserErrorHandler(new LenientErrorHandler()); + Patient parsed = (Patient) parser.parseResource(input); + assertEquals(1, parsed.getModifierExtension().size()); + assertEquals(null, parsed.getModifierExtension().get(0).getUrl()); + assertEquals("2011-01-02T11:13:15", parsed.getModifierExtension().get(0).getValueAsPrimitive().getValueAsString()); + + try { + parser = ourCtx.newXmlParser(); + parser.setParserErrorHandler(new StrictErrorHandler()); + parser.parseResource(input); + fail(); + } catch (DataFormatException e) { + assertEquals("Resource is missing required element 'url' in parent element 'modifierExtension'", e.getCause().getMessage()); + } + + } + + /** + * See #551 + */ + @Test + public void testXmlLargeAttribute() { + String largeString = StringUtils.leftPad("", (int) FileUtils.ONE_MB, 'A'); + + Patient p = new Patient(); + p.addName().setFamily(largeString); + + String encoded = ourCtx.newXmlParser().encodeResourceToString(p); + + p = ourCtx.newXmlParser().parseResource(Patient.class, encoded); + + assertEquals(largeString, p.getNameFirstRep().getFamily()); + } + + /** + * See #339 + * + * https://www.owasp.org/index.php/XML_External_Entity_(XXE)_Processing + */ + @Test + public void testXxe() { + + String input = "" + + "" + + "]>" + + "" + + "" + + "
TEXT &xxe; TEXT
" + + "
" + + "
" + + "" + + "
" + + "
"; + + ourLog.info(input); + + try { + ourCtx.newXmlParser().parseResource(Patient.class, input); + fail(); + } catch (DataFormatException e) { + assertThat(e.toString(), containsString("Undeclared general entity")); + } + + } + + @AfterClass + public static void afterClassClearContext() { + TestUtil.clearAllStaticFieldsForUnitTest(); + } + + @BeforeClass + public static void beforeClass() { + XMLUnit.setIgnoreAttributeOrder(true); + XMLUnit.setIgnoreComments(true); + XMLUnit.setIgnoreWhitespace(true); + } + + public static void main(String[] args) { + IGenericClient c = ourCtx.newRestfulGenericClient("http://fhir-dev.healthintersections.com.au/open"); + // c.registerInterceptor(new LoggingInterceptor(true)); + c.read().resource("Patient").withId("324").execute(); + } + + @ResourceDef(name = "Patient") + public static class TestPatientFor327 extends Patient { + + private static final long serialVersionUID = 1L; + + @Child(name = "testCondition") + @ca.uhn.fhir.model.api.annotation.Extension(url = "testCondition", definedLocally = true, isModifier = false) + private List testConditions = null; + + public List getConditions() { + return this.testConditions; + } + + public void setCondition(List ref) { + this.testConditions = ref; + } + } } diff --git a/src/changes/changes.xml b/src/changes/changes.xml index 88a4e8edbdc..70397ab8923 100644 --- a/src/changes/changes.xml +++ b/src/changes/changes.xml @@ -97,6 +97,10 @@ JPA server did not correctly support searching on a custom search parameter whose path pointed to an extension, where the client used a chained value. + + Fix issue where the JSON parser sometimes did not encode DSTU3 extensions on the root of a + resource which have a value of type reference. +