Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -5,10 +5,12 @@
import java.util.stream.Stream;

import org.hl7.fhir.r4.model.BooleanType;
import org.hl7.fhir.r4.model.Coding;
import org.hl7.fhir.r4.model.DateTimeType;
import org.hl7.fhir.r4.model.DateType;
import org.hl7.fhir.r4.model.DecimalType;
import org.hl7.fhir.r4.model.IntegerType;
import org.hl7.fhir.r4.model.Quantity;
import org.hl7.fhir.r4.model.Questionnaire;
import org.hl7.fhir.r4.model.QuestionnaireResponse;
import org.hl7.fhir.r4.model.Reference;
Expand Down Expand Up @@ -90,6 +92,12 @@ public Type transformQuestionTypeToAnswerType(Questionnaire.QuestionnaireItemCom
case DATETIME -> new DateTimeType("1900-01-01T00:00:00.000Z");
case URL -> new UriType("http://example.org/foo");
case REFERENCE -> new Reference("http://example.org/fhir/Placeholder/id");
case CHOICE -> new Coding().setSystem("http://example.org/fhir/CodeSystem/name").setCode("code");
case QUANTITY -> new Quantity().setValue(0).setUnit("unit")
.setSystem("http://example.org/fhir/CodeSystem/name").setCode("code");
// TODO: False positive validation error for QuestionnaireResponse.item.answer.valueQuantity.comparator,
// add comparator to Quantity as soon as https://github.com/hapifhir/org.hl7.fhir.core/issues/2224 is fixed
// .setComparator(Quantity.QuantityComparator.LESS_OR_EQUAL);

default -> throw new RuntimeException("Type '" + question.getType().getDisplay()
+ "' in Questionnaire.item is not supported as answer type");
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,10 +6,12 @@
import java.util.List;

import org.hl7.fhir.r4.model.BooleanType;
import org.hl7.fhir.r4.model.Coding;
import org.hl7.fhir.r4.model.DateTimeType;
import org.hl7.fhir.r4.model.DateType;
import org.hl7.fhir.r4.model.DecimalType;
import org.hl7.fhir.r4.model.IntegerType;
import org.hl7.fhir.r4.model.Quantity;
import org.hl7.fhir.r4.model.Questionnaire;
import org.hl7.fhir.r4.model.QuestionnaireResponse;
import org.hl7.fhir.r4.model.Reference;
Expand Down Expand Up @@ -175,15 +177,16 @@ public void testQuestionTypeReferenceToAnswerType()
assertTrue(type instanceof Reference);
}

@Test(expected = RuntimeException.class)
@Test
public void testQuestionTypeChoiceToAnswerType()
{
QuestionnaireResponseHelper qrh = new QuestionnaireResponseHelperImpl("https://foo/fhir");

Questionnaire.QuestionnaireItemComponent question = new Questionnaire.QuestionnaireItemComponent()
.setType(Questionnaire.QuestionnaireItemType.CHOICE);

qrh.transformQuestionTypeToAnswerType(question);
Type type = qrh.transformQuestionTypeToAnswerType(question);
assertTrue(type instanceof Coding);
}

@Test(expected = RuntimeException.class)
Expand All @@ -197,15 +200,16 @@ public void testQuestionTypeOpenChoiceToAnswerType()
qrh.transformQuestionTypeToAnswerType(question);
}

@Test(expected = RuntimeException.class)
@Test
public void testQuestionTypeQuantityToAnswerType()
{
QuestionnaireResponseHelper qrh = new QuestionnaireResponseHelperImpl("https://foo/fhir");

Questionnaire.QuestionnaireItemComponent question = new Questionnaire.QuestionnaireItemComponent()
.setType(Questionnaire.QuestionnaireItemType.QUANTITY);

qrh.transformQuestionTypeToAnswerType(question);
Type type = qrh.transformQuestionTypeToAnswerType(question);
assertTrue(type instanceof Quantity);
}

@Test(expected = RuntimeException.class)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@
import org.hl7.fhir.r4.model.Extension;
import org.hl7.fhir.r4.model.Identifier;
import org.hl7.fhir.r4.model.IntegerType;
import org.hl7.fhir.r4.model.Quantity;
import org.hl7.fhir.r4.model.Questionnaire;
import org.hl7.fhir.r4.model.QuestionnaireResponse;
import org.hl7.fhir.r4.model.Reference;
Expand Down Expand Up @@ -95,6 +96,12 @@ public Type transformQuestionTypeToAnswerType(Questionnaire.QuestionnaireItemCom
case DATETIME -> new DateTimeType("1900-01-01T00:00:00.000Z");
case URL -> new UriType("http://example.org/foo");
case REFERENCE -> new Reference("http://example.org/fhir/Placeholder/id");
case CHOICE -> new Coding().setSystem("http://example.org/fhir/CodeSystem/name").setCode("code");
case QUANTITY -> new Quantity().setValue(0).setUnit("unit")
.setSystem("http://example.org/fhir/CodeSystem/name").setCode("code");
// TODO: False positive validation error for QuestionnaireResponse.item.answer.valueQuantity.comparator,
// add comparator to Quantity as soon as https://github.com/hapifhir/org.hl7.fhir.core/issues/2224 is fixed
// .setComparator(Quantity.QuantityComparator.LESS_OR_EQUAL);

default -> throw new RuntimeException("Type '" + question.getType().getDisplay()
+ "' in Questionnaire.item is not supported as answer type");
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@
import org.hl7.fhir.r4.model.Extension;
import org.hl7.fhir.r4.model.Identifier;
import org.hl7.fhir.r4.model.IntegerType;
import org.hl7.fhir.r4.model.Quantity;
import org.hl7.fhir.r4.model.QuestionnaireResponse;
import org.hl7.fhir.r4.model.QuestionnaireResponse.QuestionnaireResponseItemComponent;
import org.hl7.fhir.r4.model.QuestionnaireResponse.QuestionnaireResponseStatus;
Expand Down Expand Up @@ -192,6 +193,11 @@ else if ("identifiers".equals(type))
.setValue("External_Test_Organization")));

case "boolean-example" -> set(item, new BooleanType(true));

case "choice-example" ->
set(item, new Coding().setSystem("http://example.org/fhir/CodeSystem/name").setCode("code"));

case "quantity-example" -> set(item, new Quantity().setValue(0).setUnit("unit"));
}
});

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -15,13 +15,15 @@
import org.hl7.fhir.r4.model.BooleanType;
import org.hl7.fhir.r4.model.Bundle;
import org.hl7.fhir.r4.model.Bundle.BundleEntryComponent;
import org.hl7.fhir.r4.model.Coding;
import org.hl7.fhir.r4.model.DateTimeType;
import org.hl7.fhir.r4.model.DateType;
import org.hl7.fhir.r4.model.DecimalType;
import org.hl7.fhir.r4.model.IdType;
import org.hl7.fhir.r4.model.Identifier;
import org.hl7.fhir.r4.model.IntegerType;
import org.hl7.fhir.r4.model.PrimitiveType;
import org.hl7.fhir.r4.model.Quantity;
import org.hl7.fhir.r4.model.QuestionnaireResponse;
import org.hl7.fhir.r4.model.QuestionnaireResponse.QuestionnaireResponseItemComponent;
import org.hl7.fhir.r4.model.QuestionnaireResponse.QuestionnaireResponseStatus;
Expand Down Expand Up @@ -125,6 +127,11 @@ public void checkQuestionnaireResponse(ProcessPluginApi api) throws Exception
.setValue("External_Test_Organization")));

case "boolean-example" -> test(item, new BooleanType(true));

case "choice-example" ->
test(item, new Coding().setSystem("http://example.org/fhir/CodeSystem/name").setCode("code"));

case "quantity-example" -> test(item, new Quantity().setValue(0).setUnit("unit"));
}
});

Expand Down Expand Up @@ -159,6 +166,21 @@ private void test(QuestionnaireResponseItemComponent item, Type expected)
expectTrue(r.getIdentifier().hasValue());
expectSame(((Reference) expected).getIdentifier().getSystem(), r.getIdentifier().getSystem());
expectSame(((Reference) expected).getIdentifier().getValue(), r.getIdentifier().getValue());

}

case Coding c -> {
expectTrue(c.hasSystem());
expectSame(((Coding) expected).getSystem(), c.getSystem());
expectTrue(c.hasCode());
expectSame(((Coding) expected).getCode(), c.getCode());
}

case Quantity q -> {
expectTrue(q.hasValue());
expectSame(((Quantity) expected).getValue(), q.getValue());
expectTrue(q.hasUnit());
expectSame(((Quantity) expected).getUnit(), q.getUnit());
}

default ->
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -91,4 +91,16 @@
<text value="Do you approve the release of the data-set?" />
<required value="false" />
</item>
<item>
<linkId value="choice-example" />
<type value="choice" />
<text value="Add a coding to test the choice type" />
<required value="false" />
</item>
<item>
<linkId value="quantity-example" />
<type value="quantity" />
<text value="Add a quantity to test the quantity type" />
<required value="false" />
</item>
</Questionnaire>
Original file line number Diff line number Diff line change
@@ -0,0 +1,57 @@
package dev.dsf.fhir.adapter;

import java.math.BigDecimal;

import org.hl7.fhir.r4.model.Quantity;

public final class ElementQuantityValue
{
public static <R extends Quantity> ElementQuantityValue from(R element)
{
return new ElementQuantityValue(element.hasSystem() ? element.getSystem() : null,
element.hasCode() ? element.getCode() : null, element.hasUnit() ? element.getUnit() : null,
element.hasValue() ? element.getValue() : null,
element.hasComparator() ? element.getComparator() : null);
}

private final String system;
private final String code;
private final String unit;
private final BigDecimal value;
private final Quantity.QuantityComparator comparator;

private ElementQuantityValue(String system, String code, String unit, BigDecimal value,
Quantity.QuantityComparator comparator)
{
this.system = system;
this.code = code;
this.unit = unit;
this.value = value;
this.comparator = comparator;
}

public String getSystem()
{
return system;
}

public String getCode()
{
return code;
}

public String getUnit()
{
return unit;
}

public BigDecimal getValue()
{
return value;
}

public String getComparator()
{
return comparator != null ? comparator.toCode() : null;
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@
import org.hl7.fhir.r4.model.DateType;
import org.hl7.fhir.r4.model.DecimalType;
import org.hl7.fhir.r4.model.IntegerType;
import org.hl7.fhir.r4.model.Quantity;
import org.hl7.fhir.r4.model.QuestionnaireResponse;
import org.hl7.fhir.r4.model.QuestionnaireResponse.QuestionnaireResponseItemAnswerComponent;
import org.hl7.fhir.r4.model.QuestionnaireResponse.QuestionnaireResponseItemComponent;
Expand Down Expand Up @@ -39,7 +40,7 @@ private record Element(String questionnaire, String businessKey, String userTask
}

private record Item(boolean show, String id, String type, String label, String fhirType, String stringValue,
ElementSystemValue systemValueValue, Boolean booleanValue)
ElementSystemValue systemValueValue, Boolean booleanValue, ElementQuantityValue quantityValue)
{
}

Expand Down Expand Up @@ -103,7 +104,7 @@ private Item toItem(QuestionnaireResponseItemComponent i)
if (i.hasAnswer() && i.getAnswer().size() == 1)
return toItem(show, linkId, text, i.getAnswerFirstRep().getValue());
else
return new Item(show, linkId, null, text, null, null, null, null);
return new Item(show, linkId, null, text, null, null, null, null, null);
}

private Item toItem(boolean show, String id, String label, Type typedValue)
Expand All @@ -113,39 +114,42 @@ private Item toItem(boolean show, String id, String label, Type typedValue)
return switch (typedValue)
{
case BooleanType b ->
new Item(show, id, "boolean", label, fhirType, null, null, b.hasValue() ? b.getValue() : null);
new Item(show, id, "boolean", label, fhirType, null, null, b.hasValue() ? b.getValue() : null, null);

case DecimalType d -> new Item(show, id, "number", label, fhirType,
d.hasValue() ? String.valueOf(d.getValue()) : null, null, null);
d.hasValue() ? String.valueOf(d.getValue()) : null, null, null, null);

case IntegerType i -> new Item(show, id, "number", label, fhirType,
i.hasValue() ? String.valueOf(i.getValue()) : null, null, null);
i.hasValue() ? String.valueOf(i.getValue()) : null, null, null, null);

case DateType d -> new Item(show, id, "date", label, fhirType,
d.hasValue() ? format(d.getValue(), DATE_FORMAT) : null, null, null);
d.hasValue() ? format(d.getValue(), DATE_FORMAT) : null, null, null, null);

case DateTimeType dt -> new Item(show, id, "datetime-local", label, fhirType,
dt.hasValue() ? format(dt.getValue(), DATE_TIME_FORMAT) : null, null, null);
dt.hasValue() ? format(dt.getValue(), DATE_TIME_FORMAT) : null, null, null, null);

case TimeType t ->
new Item(show, id, "time", label, fhirType, t.hasValue() ? t.getValue() : null, null, null);
new Item(show, id, "time", label, fhirType, t.hasValue() ? t.getValue() : null, null, null, null);

case StringType s ->
new Item(show, id, "text", label, fhirType, s.hasValue() ? s.getValue() : null, null, null);
new Item(show, id, "text", label, fhirType, s.hasValue() ? s.getValue() : null, null, null, null);

case UriType u ->
new Item(show, id, "url", label, fhirType, u.hasValue() ? u.getValue() : null, null, null);
new Item(show, id, "url", label, fhirType, u.hasValue() ? u.getValue() : null, null, null, null);

case Coding c -> new Item(show, id, "coding", label, fhirType, null, ElementSystemValue.from(c), null);
case Coding c ->
new Item(show, id, "coding", label, fhirType, null, ElementSystemValue.from(c), null, null);

case Reference r when r.hasReferenceElement() -> new Item(show, id, "url", label, fhirType + ".reference",
r.getReferenceElement().hasValue() ? r.getReferenceElement().getValue() : null, null, null);
r.getReferenceElement().hasValue() ? r.getReferenceElement().getValue() : null, null, null, null);

case Reference r when r.hasIdentifier() -> new Item(show, id, "identifier", label, fhirType + ".identifier",
null, ElementSystemValue.from(r.getIdentifier()), null);
null, ElementSystemValue.from(r.getIdentifier()), null, null);

case Quantity q ->
new Item(show, id, "quantity", label, fhirType, null, null, null, ElementQuantityValue.from(q));

// TODO case Attachment a ->
// TODO case Quantity q ->

default -> {
logger.warn("Element of type {}, not supported", fhirType);
Expand Down
Loading