diff --git a/src/main/java/org/opencds/cqf/tooling/visitor/ElmOperatorRequirement.java b/src/main/java/org/opencds/cqf/tooling/visitor/ElmOperatorRequirement.java new file mode 100644 index 000000000..c19dbf446 --- /dev/null +++ b/src/main/java/org/opencds/cqf/tooling/visitor/ElmOperatorRequirement.java @@ -0,0 +1,26 @@ +package org.opencds.cqf.tooling.visitor; + +import org.hl7.elm.r1.Expression; +import org.hl7.elm.r1.VersionedIdentifier; + +import java.util.HashSet; +import java.util.LinkedHashSet; + +public class ElmOperatorRequirement extends ElmExpressionRequirement { + private HashSet requirements = new LinkedHashSet(); + public Iterable getRequirements() { + return requirements; + } + + public ElmOperatorRequirement(VersionedIdentifier libraryIdentifier, Expression expression) { + super(libraryIdentifier, expression); + } + + @Override + public ElmExpressionRequirement combine(ElmExpressionRequirement requirement) { + if (requirement != null) { + requirements.add(requirement); + } + return this; + } +} diff --git a/src/main/java/org/opencds/cqf/tooling/visitor/ElmRequirementsVisitor.java b/src/main/java/org/opencds/cqf/tooling/visitor/ElmRequirementsVisitor.java index d65328719..c7fe81b72 100644 --- a/src/main/java/org/opencds/cqf/tooling/visitor/ElmRequirementsVisitor.java +++ b/src/main/java/org/opencds/cqf/tooling/visitor/ElmRequirementsVisitor.java @@ -3,6 +3,8 @@ import org.cqframework.cql.elm.visiting.ElmBaseLibraryVisitor; import org.hl7.elm.r1.*; +import java.util.Iterator; + public class ElmRequirementsVisitor extends ElmBaseLibraryVisitor { public ElmRequirementsVisitor() { @@ -285,18 +287,29 @@ public ElmRequirement visitChildren(BinaryExpression elm, ElmRequirementsContext */ // TODO: Normalize to DNF case "And": { - ElmExpressionRequirement left = (ElmExpressionRequirement)visitElement(elm.getOperand().get(0), context); - ElmExpressionRequirement right = (ElmExpressionRequirement)visitElement(elm.getOperand().get(1), context); + ElmRequirement left = visitElement(elm.getOperand().get(0), context); + ElmRequirement right = visitElement(elm.getOperand().get(1), context); - return new ElmConjunctiveRequirement(context.getCurrentLibraryIdentifier(), (And)elm).combine(left).combine(right); + if (left instanceof ElmExpressionRequirement && right instanceof ElmExpressionRequirement) { + return new ElmConjunctiveRequirement(context.getCurrentLibraryIdentifier(), elm) + .combine((ElmExpressionRequirement)left) + .combine((ElmExpressionRequirement)right); + } + + throw new IllegalArgumentException("Expected ElmExpressionRequirement"); } case "Or": { + ElmRequirement left = visitElement(elm.getOperand().get(0), context); + ElmRequirement right = visitElement(elm.getOperand().get(1), context); - ElmExpressionRequirement left = (ElmExpressionRequirement)visitElement(elm.getOperand().get(0), context); - ElmExpressionRequirement right = (ElmExpressionRequirement)visitElement(elm.getOperand().get(1), context); + if (left instanceof ElmExpressionRequirement && right instanceof ElmExpressionRequirement) { + return new ElmDisjunctiveRequirement(context.getCurrentLibraryIdentifier(), elm) + .combine((ElmExpressionRequirement)left) + .combine((ElmExpressionRequirement)right); + } - return new ElmDisjunctiveRequirement(context.getCurrentLibraryIdentifier(), (Or)elm).combine(left).combine(right); + throw new IllegalArgumentException("Expected ElmExpressionRequirement"); } // TODO: Rewrite @@ -417,7 +430,8 @@ public ElmRequirement visitNot(Not elm, ElmRequirementsContext context) { @Override public ElmRequirement visitIf(If elm, ElmRequirementsContext context) { - return super.visitIf(elm, context); + // TODO: Rewrite the if as equivalent logic + return new ElmOperatorRequirement(context.getCurrentLibraryIdentifier(), elm); } @Override @@ -427,12 +441,36 @@ public ElmRequirement visitCaseItem(CaseItem elm, ElmRequirementsContext context @Override public ElmRequirement visitCase(Case elm, ElmRequirementsContext context) { - return super.visitCase(elm, context); + // TODO: Rewrite the case as equivalent logic + ElmOperatorRequirement result = new ElmOperatorRequirement(context.getCurrentLibraryIdentifier(), elm); + ElmRequirement childResult = null; + if (elm.getComparand() != null) { + childResult = this.visitElement(elm.getComparand(), context); + if (childResult instanceof ElmExpressionRequirement) { + result.combine((ElmExpressionRequirement)childResult); + } + } + + for (CaseItem ci : elm.getCaseItem()) { + childResult = this.visitElement(ci, context); + if (childResult instanceof ElmExpressionRequirement) { + result.combine((ElmExpressionRequirement)childResult); + } + } + + if (elm.getElse() != null) { + childResult = this.visitElement(elm.getElse(), context); + if (childResult instanceof ElmExpressionRequirement) { + result.combine((ElmExpressionRequirement)childResult); + } + } + + return result; } @Override public ElmRequirement visitNull(Null elm, ElmRequirementsContext context) { - return super.visitNull(elm, context); + return new ElmExpressionRequirement(context.getCurrentLibraryIdentifier(), elm); } @Override @@ -726,17 +764,17 @@ public ElmRequirement visitDateTimeComponentFrom(DateTimeComponentFrom elm, ElmR @Override public ElmRequirement visitTimeOfDay(TimeOfDay elm, ElmRequirementsContext context) { - return super.visitTimeOfDay(elm, context); + return new ElmExpressionRequirement(context.getCurrentLibraryIdentifier(), elm); } @Override public ElmRequirement visitToday(Today elm, ElmRequirementsContext context) { - return super.visitToday(elm, context); + return new ElmExpressionRequirement(context.getCurrentLibraryIdentifier(), elm); } @Override public ElmRequirement visitNow(Now elm, ElmRequirementsContext context) { - return super.visitNow(elm, context); + return new ElmExpressionRequirement(context.getCurrentLibraryIdentifier(), elm); } @Override