Search in sources :

Example 16 with Invariant

use of org.hl7.fhir.definitions.model.Invariant in project kindling by HL7.

the class TableGenerator method genElement.

protected Row genElement(ElementDefn e, HierarchicalTableGenerator gen, boolean resource, String path, boolean isProfile, String prefix, RenderMode mode, boolean isRoot, StandardsStatus rootStatus, boolean isAbstract, boolean isInterface) throws Exception {
    Row row = gen.new Row();
    row.setAnchor(path);
    boolean isProfiledExtension = isProfile && (e.getName().equals("extension") || e.getName().equals("modifierExtension"));
    row.getCells().add(gen.new Cell(null, dictLinks() ? pageName + "#" + path.replace("[", "_").replace("]", "_") : null, e.getName(), path + " : " + e.getDefinition(), null));
    Cell gc = gen.new Cell();
    row.getCells().add(gc);
    if (e.hasMustSupport() && e.isMustSupport()) {
        gc.addStyledText("This element must be supported", "S", "white", "red", prefix + "conformance-rules.html#mustSupport", false);
    }
    if (e.isModifier()) {
        gc.addStyledText("This element is a modifier element", "?!", null, null, prefix + "conformance-rules.html#isModifier", false);
    }
    if (e.isSummary()) {
        gc.addStyledText("This element is included in summaries", "\u03A3", null, null, prefix + "elementdefinition-definitions.html#ElementDefinition.isSummary", false);
    }
    if (!isRoot && (!e.getInvariants().isEmpty() || !e.getStatedInvariants().isEmpty())) {
        gc.addStyledText("This element has or is affected by some invariants", "I", null, null, prefix + "conformance-rules.html#constraints", false);
    }
    if (isInterface) {
        gc.addStyledText("This is an abstract type", "«A»", null, null, prefix + "uml.html#abstract", false);
    } else if (isAbstract) {
        gc.addStyledText("This is an interface resource", "«I»", null, null, prefix + "uml.html#interface", false);
    }
    if (rootStatus != null)
        gc.addStyledText("Standards Status = " + rootStatus.toDisplay(), rootStatus.getAbbrev(), "black", rootStatus.getColor(), prefix + "versions.html#std-process", true);
    else if (e.getStandardsStatus() != null)
        gc.addStyledText("Standards Status = " + e.getStandardsStatus().toDisplay(), e.getStandardsStatus().getAbbrev(), "black", e.getStandardsStatus().getColor(), prefix + "versions.html#std-process", true);
    if (resource) {
        row.getCells().add(gen.new Cell());
        row.setIcon("icon_resource.png", HierarchicalTableGenerator.TEXT_ICON_RESOURCE);
        if (Utilities.noString(e.typeCode()))
            row.getCells().add(gen.new Cell(null, null, "n/a", null, null));
        else if ("Logical".equals(e.typeCode()))
            row.getCells().add(gen.new Cell(null, prefix + "structuredefinition.html#logical", e.typeCode(), null, null));
        else if ("Base".equals(e.typeCode()))
            row.getCells().add(gen.new Cell(null, prefix + definitions.getSrcFile("Base") + ".html#" + e.typeCode(), e.typeCode(), null, null));
        else
            row.getCells().add(gen.new Cell(null, prefix + e.typeCode().toLowerCase() + ".html", e.typeCode(), null, null));
    // todo: base elements
    } else {
        if (!e.getElements().isEmpty()) {
            row.getCells().add(gen.new Cell(null, null, path.contains(".") ? e.describeCardinality() : "", null, null));
            row.setIcon("icon_element.gif", HierarchicalTableGenerator.TEXT_ICON_ELEMENT);
            if (mode == RenderMode.RESOURCE)
                row.getCells().add(gen.new Cell(null, prefix + definitions.getBackboneLink(), "BackboneElement", null, null));
            else if (e.getName().equals("Type"))
                row.getCells().add(gen.new Cell(null, null, "", null, null));
            else if (e.getName().equals("Element")) {
                if (version.isR4B()) {
                    row.getCells().add(gen.new Cell(null, prefix + definitions.getElementLink(), "Element", null, null));
                } else {
                    row.getCells().add(gen.new Cell(null, prefix + definitions.getBaseLink(), "Base", null, null));
                }
            } else if (e.typeCode().equals("BackboneElement"))
                row.getCells().add(gen.new Cell(null, prefix + definitions.getBackboneLink(), "BackBoneElement", null, null));
            else
                row.getCells().add(gen.new Cell(null, prefix + definitions.getElementLink(), "Element", null, null));
        } else if (e.getTypes().size() == 1) {
            row.getCells().add(gen.new Cell(null, null, path.contains(".") ? e.describeCardinality() : "", null, null));
            String t = e.getTypes().get(0).getName();
            Cell c;
            if (t.startsWith("@")) {
                row.setIcon("icon_reuse.png", HierarchicalTableGenerator.TEXT_ICON_REUSE);
                c = gen.new Cell("see ", "#" + t.substring(1), t.substring(t.lastIndexOf(".") + 1), t.substring(1), null);
            } else if (isReference(t)) {
                row.setIcon("icon_reference.png", HierarchicalTableGenerator.TEXT_ICON_REFERENCE);
                c = gen.new Cell();
                if (ADD_REFERENCE_TO_TABLE) {
                    c.getPieces().add(gen.new Piece(prefix + definitions.getSrcFile(t) + ".html#" + t, t, null));
                    c.getPieces().add(gen.new Piece(null, "(", null));
                }
                boolean first = true;
                for (String rt : e.getTypes().get(0).getParams()) {
                    if (!first)
                        c.getPieces().add(gen.new Piece(null, " | ", null));
                    if (first && isProfile && e.getTypes().get(0).getProfile() != null)
                        c.getPieces().add(gen.new Piece(null, e.getTypes().get(0).getProfile(), null));
                    else
                        c.getPieces().add(gen.new Piece(prefix + findPage(rt) + ".html", rt, null));
                    first = false;
                }
                if (ADD_REFERENCE_TO_TABLE)
                    c.getPieces().add(gen.new Piece(null, ")", null));
            } else if (definitions.getPrimitives().containsKey(t)) {
                row.setIcon("icon_primitive.png", HierarchicalTableGenerator.TEXT_ICON_PRIMITIVE);
                c = gen.new Cell(null, prefix + "datatypes.html#" + t, t, null, null);
            } else {
                if (t.equals("Extension"))
                    row.setIcon("icon_extension_simple.png", HierarchicalTableGenerator.TEXT_ICON_EXTENSION);
                else
                    row.setIcon("icon_datatype.gif", HierarchicalTableGenerator.TEXT_ICON_DATATYPE);
                c = gen.new Cell(null, prefix + definitions.getSrcFile(t) + ".html#" + t.replace("*", "open"), t, null, null);
            }
            row.getCells().add(c);
        } else {
            row.getCells().add(gen.new Cell(null, null, isRoot ? "" : e.describeCardinality(), null, null));
            row.setIcon("icon_choice.gif", HierarchicalTableGenerator.TEXT_ICON_CHOICE);
            row.getCells().add(gen.new Cell(null, null, "", null, null));
        }
    }
    Cell cc = gen.new Cell(null, e.getShortDefn() != null && Utilities.isURL(e.getShortDefn()) ? e.getShortDefn() : null, e.getShortDefn(), null, null);
    row.getCells().add(cc);
    // constraints
    if (isProfiledExtension) {
        cc.addPiece(gen.new Piece("br"));
        cc.getPieces().add(gen.new Piece(null, e.getTypes().get(0).getProfile(), null));
    }
    if (e.hasBinding() && e.getBinding() != null && e.getBinding().getBinding() != BindingMethod.Unbound) {
        if (cc.getPieces().size() == 1)
            cc.addPiece(gen.new Piece("br"));
        cc.getPieces().add(gen.new Piece(getBindingLink(prefix, e), e.getBinding().getValueSet() != null ? e.getBinding().getValueSet().present() : e.getBinding().getName(), e.getBinding().getDefinition()));
        cc.getPieces().add(gen.new Piece(null, " (", null));
        BindingSpecification b = e.getBinding();
        if (b.hasMax()) {
            cc.getPieces().add(gen.new Piece(prefix + "terminologies.html#" + b.getStrength().toCode(), b.getStrength().getDisplay(), b.getStrength().getDefinition()));
            cc.getPieces().add(gen.new Piece(null, " but limited to ", null));
            ValueSet vs = b.getMaxValueSet();
            if (vs == null)
                cc.getPieces().add(gen.new Piece(b.getMaxReference(), b.getMaxReference(), null));
            else
                cc.getPieces().add(gen.new Piece(vs.hasUserData("external.url") ? vs.getUserString("external.url") : vs.getUserString("path"), vs.getName(), null));
        } else
            cc.getPieces().add(gen.new Piece(prefix + "terminologies.html#" + b.getStrength().toCode(), b.getStrength().getDisplay(), b.getStrength().getDefinition()));
        cc.getPieces().add(gen.new Piece(null, ")", null));
    }
    List<String> invs = new ArrayList<String>(e.getInvariants().keySet());
    Collections.sort(invs, new ConstraintsSorter());
    for (String name : invs) {
        Invariant inv = e.getInvariants().get(name);
        cc.addPiece(gen.new Piece("br"));
        cc.getPieces().add(gen.new Piece(null, "+ " + presentLevel(inv) + ": " + inv.getEnglish(), inv.getId()).setStyle("font-style: italic"));
    }
    if (e.unbounded() && !isRoot) {
        if (cc.getPieces().size() > 0)
            cc.addPiece(gen.new Piece("br"));
        if (Utilities.noString(e.getOrderMeaning())) {
        // don't show this, this it's important: cc.getPieces().add(gen.new Piece(null, "This repeating element has no defined order", null));
        } else {
            cc.getPieces().add(gen.new Piece(null, "This repeating element order: " + e.getOrderMeaning(), null));
        }
    }
    if (isRoot && !Utilities.noString(e.typeCode()) && !"Logical".equals(e.typeCode())) {
        List<ElementDefn> ancestors = new ArrayList<ElementDefn>();
        ElementDefn f = definitions.getElementDefn(e.typeCode());
        while (f != null) {
            ancestors.add(0, f);
            f = Utilities.noString(f.typeCode()) || "Logical".equals(f.typeCode()) ? null : definitions.getElementDefn(f.typeCode());
        }
        cc.getPieces().add(gen.new Piece("br"));
        cc.getPieces().add(gen.new Piece(null, "Elements defined in Ancestors: ", null));
        boolean first = true;
        for (ElementDefn fi : ancestors) {
            for (ElementDefn fc : fi.getElements()) {
                if (first)
                    first = false;
                else
                    cc.getPieces().add(gen.new Piece(null, ", ", null));
                cc.getPieces().add(gen.new Piece(definitions.getSrcFile(fi.getName()) + ".html#" + fi.getName(), fc.getName(), fc.getDefinition()));
            }
        }
    }
    if (mode == RenderMode.LOGICAL) {
        String logical = e.getMappings().get("http://hl7.org/fhir/logical");
        Cell c = gen.new Cell();
        row.getCells().add(c);
        if (logical != null)
            presentLogicalMapping(gen, c, logical, prefix);
    }
    if (e.getTypes().size() > 1) {
        // create a child for each choice
        for (TypeRef tr : e.getTypes()) {
            Row choicerow = gen.new Row();
            String t = tr.getName();
            if (isReference(t)) {
                choicerow.getCells().add(gen.new Cell(null, null, e.getName().replace("[x]", Utilities.capitalize(t)), null, null));
                choicerow.getCells().add(gen.new Cell());
                choicerow.getCells().add(gen.new Cell(null, null, "", null, null));
                choicerow.setIcon("icon_reference.png", HierarchicalTableGenerator.TEXT_ICON_REFERENCE);
                Cell c = gen.new Cell();
                choicerow.getCells().add(c);
                if (ADD_REFERENCE_TO_TABLE) {
                    if (tr.getName().equals("canonical"))
                        c.getPieces().add(gen.new Piece(prefix + "datatypes.html#canonical", "canonical", null));
                    else
                        c.getPieces().add(gen.new Piece(prefix + "references.html#Reference", "Reference", null));
                    c.getPieces().add(gen.new Piece(null, "(", null));
                }
                boolean first = true;
                for (String rt : tr.getParams()) {
                    if (!first)
                        c.getPieces().add(gen.new Piece(null, " | ", null));
                    c.getPieces().add(gen.new Piece(prefix + findPage(rt) + ".html", rt, null));
                    first = false;
                }
                if (ADD_REFERENCE_TO_TABLE)
                    c.getPieces().add(gen.new Piece(null, ")", null));
            } else if (definitions.getPrimitives().containsKey(t)) {
                choicerow.getCells().add(gen.new Cell(null, null, e.getName().replace("[x]", Utilities.capitalize(t)), definitions.getPrimitives().get(t).getDefinition(), null));
                choicerow.getCells().add(gen.new Cell());
                choicerow.getCells().add(gen.new Cell(null, null, "", null, null));
                choicerow.setIcon("icon_primitive.png", HierarchicalTableGenerator.TEXT_ICON_PRIMITIVE);
                choicerow.getCells().add(gen.new Cell(null, prefix + "datatypes.html#" + t, t, null, null));
            } else if (definitions.getConstraints().containsKey(t)) {
                ProfiledType pt = definitions.getConstraints().get(t);
                choicerow.getCells().add(gen.new Cell(null, null, e.getName().replace("[x]", Utilities.capitalize(pt.getBaseType())), definitions.getTypes().containsKey(t) ? definitions.getTypes().get(t).getDefinition() : null, null));
                choicerow.getCells().add(gen.new Cell());
                choicerow.getCells().add(gen.new Cell(null, null, "", null, null));
                choicerow.setIcon("icon_datatype.gif", HierarchicalTableGenerator.TEXT_ICON_DATATYPE);
                choicerow.getCells().add(gen.new Cell(null, definitions.getSrcFile(t) + ".html#" + t.replace("*", "open"), t, null, null));
            } else {
                choicerow.getCells().add(gen.new Cell(null, null, e.getName().replace("[x]", Utilities.capitalize(t)), definitions.getTypes().containsKey(t) ? definitions.getTypes().get(t).getDefinition() : null, null));
                choicerow.getCells().add(gen.new Cell());
                choicerow.getCells().add(gen.new Cell(null, null, "", null, null));
                choicerow.setIcon("icon_datatype.gif", HierarchicalTableGenerator.TEXT_ICON_DATATYPE);
                choicerow.getCells().add(gen.new Cell(null, definitions.getSrcFile(t) + ".html#" + t.replace("*", "open"), t, null, null));
            }
            choicerow.getCells().add(gen.new Cell());
            // choicerow.getCells().add(gen.new Cell());
            row.getSubRows().add(choicerow);
        }
    } else
        for (ElementDefn c : e.getElements()) {
            row.getSubRows().add(genElement(c, gen, false, path + '.' + c.getName(), isProfile, prefix, mode, false, null, false, false));
        }
    return row;
}
Also used : Invariant(org.hl7.fhir.definitions.model.Invariant) ProfiledType(org.hl7.fhir.definitions.model.ProfiledType) TypeRef(org.hl7.fhir.definitions.model.TypeRef) ArrayList(java.util.ArrayList) ElementDefn(org.hl7.fhir.definitions.model.ElementDefn) BindingSpecification(org.hl7.fhir.definitions.model.BindingSpecification) Row(org.hl7.fhir.utilities.xhtml.HierarchicalTableGenerator.Row) Cell(org.hl7.fhir.utilities.xhtml.HierarchicalTableGenerator.Cell) ValueSet(org.hl7.fhir.r5.model.ValueSet)

Example 17 with Invariant

use of org.hl7.fhir.definitions.model.Invariant in project kindling by HL7.

the class ProfileGenerator method createBaseDefinition.

private ElementDefinition createBaseDefinition(StructureDefinition p, String path, ElementDefn src) throws Exception {
    ElementDefinition ce = new ElementDefinition(true, ElementDefinition.NOT_MODIFIER, ElementDefinition.NOT_IN_SUMMARY);
    ce.setId(path + "." + src.getName());
    ce.setPath(path + "." + src.getName());
    ce.setShort(src.getShortDefn());
    ce.setDefinition(preProcessMarkdown(src.getDefinition(), "ELement Definition"));
    ce.setComment(preProcessMarkdown(src.getComments(), "Element Comments"));
    ce.setRequirements(preProcessMarkdown(src.getRequirements(), "Element Reqiurements"));
    for (String a : src.getAliases()) ce.addAlias(a);
    ce.setMin(src.getMinCardinality());
    if (src.getMaxCardinality() != null)
        ce.setMax(src.getMaxCardinality() == Integer.MAX_VALUE ? "*" : src.getMaxCardinality().toString());
    ce.getType(src.typeCode());
    // this one should never be used
    if (!Utilities.noString(src.getTypes().get(0).getProfile())) {
        if (ce.getType().equals("Reference") || ce.getType().equals("canonical") || ce.getType().equals("CodeableReference"))
            throw new Error("Should not happen");
        ce.getType().get(0).addProfile(src.getTypes().get(0).getProfile());
    }
    // todo? conditions, constraints, binding, mapping
    if (src.hasModifier())
        ce.setIsModifier(src.isModifier());
    if (ce.getIsModifier())
        ce.setIsModifierReason(src.getModifierReason());
    if (src.hasSummaryItem())
        ce.setIsSummaryElement(Factory.newBoolean(src.isSummary()));
    for (Invariant id : src.getStatedInvariants()) ce.addCondition(id.getId());
    return ce;
}
Also used : Invariant(org.hl7.fhir.definitions.model.Invariant) FHIRFormatError(org.hl7.fhir.exceptions.FHIRFormatError) ElementDefinition(org.hl7.fhir.r5.model.ElementDefinition)

Example 18 with Invariant

use of org.hl7.fhir.definitions.model.Invariant in project kindling by HL7.

the class DictHTMLGenerator method listInvariants.

public void listInvariants(List<ElementDefinitionConstraintComponent> constraints, StringBuilder s, boolean inherited, String title, StructureDefinition sd) throws FHIRException, Exception {
    List<String> ids = new ArrayList<String>();
    for (ElementDefinitionConstraintComponent id : constraints) {
        if (inherited == isInherited(id, sd))
            ids.add(id.getKey());
    }
    if (ids.size() > 0) {
        Collections.sort(ids, new ConstraintsSorter());
        if (s.length() == 0)
            s.append("<table class=\"dict\">\r\n");
        s.append("<tr><td colspan=\"4\"><b>" + title + "</b></td></tr>\r\n");
        for (String id : ids) {
            ElementDefinitionConstraintComponent inv = getConstraint(constraints, id);
            s.append("<tr><td width=\"60px\"><b title=\"Formal Invariant Identifier\">" + inv.getKey() + "</b></td><td>" + presentLevel(inv) + "</td><td>" + Utilities.escapeXml(inv.getHuman()) + "</td><td><span style=\"font-family: Courier New, monospace\">" + Utilities.escapeXml(inv.getExpression()) + "</span>");
            if (inv.hasExtension("http://hl7.org/fhir/StructureDefinition/elementdefinition-bestpractice"))
                s.append("<br/>This is (only) a best practice guideline because: <blockquote>" + page.processMarkdown("best practice guideline", inv.getExtensionString("http://hl7.org/fhir/StructureDefinition/elementdefinition-bestpractice-explanation"), prefix) + "</blockquote>");
            s.append("</td></tr>");
        }
    }
}
Also used : ArrayList(java.util.ArrayList) ElementDefinitionConstraintComponent(org.hl7.fhir.r5.model.ElementDefinition.ElementDefinitionConstraintComponent)

Example 19 with Invariant

use of org.hl7.fhir.definitions.model.Invariant in project kindling by HL7.

the class OldSpreadsheetParser method processLine.

private ElementDefn processLine(ResourceDefn root, Sheet sheet, int row, Map<String, Invariant> invariants, boolean profile, Profile pack, boolean firstTime) throws Exception {
    ElementDefn e;
    String path = sheet.getColumn(row, "Element");
    if (path.startsWith("!"))
        return null;
    if (Utilities.noString(path))
        throw new Exception("Error reading definitions - no path found @ " + getLocation(row));
    if (path.contains("#"))
        throw new Exception("Old path style @ " + getLocation(row));
    String profileName = isProfile ? sheet.getColumn(row, "Profile Name") : "";
    String discriminator = isProfile ? sheet.getColumn(row, "Discriminator") : "";
    boolean isRoot = !path.contains(".");
    if (isRoot) {
        if (root.getRoot() != null)
            throw new Exception("Definitions in " + getLocation(row) + " contain two roots: " + path + " in " + root.getName());
        root.setName(path);
        e = new TypeDefn();
        e.setName(path);
        root.setRoot((TypeDefn) e);
        if (template != null)
            e.copyFrom(template.getRoot(), root.getName(), templateTitle);
    } else {
        e = makeFromPath(root.getRoot(), path, row, profileName, true);
        if (template != null) {
            ElementDefn ted = getTemplateDefinition(path);
            if (ted != null) {
                e.copyFrom(ted, root.getName(), templateTitle);
            }
        }
    }
    e.setStandardsStatus(StandardsStatus.fromCode(sheet.getColumn(row, "Standards-Status")));
    e.setNormativeVersion(sheet.getColumn(row, "Normative-Version"));
    if (e.getName().startsWith("@")) {
        e.setName(e.getName().substring(1));
        e.setXmlAttribute(true);
    }
    String c = sheet.getColumn(row, "Card.");
    if (c == null || c.equals("") || c.startsWith("!")) {
        if (!isRoot && !profile && (template == null))
            throw new Exception("Missing cardinality at " + getLocation(row) + " on " + path);
        if (isRoot && (template == null)) {
            e.setMinCardinality(0);
            e.setMaxCardinality(Integer.MAX_VALUE);
        }
    } else {
        String[] card = c.split("\\.\\.");
        if (card.length != 2 || !Utilities.isInteger(card[0]) || (!"*".equals(card[1]) && !Utilities.isInteger(card[1])))
            throw new Exception("Unable to parse Cardinality '" + c + "' " + c + " in " + getLocation(row) + " on " + path);
        e.setMinCardinality(Integer.parseInt(card[0]));
        e.setMaxCardinality("*".equals(card[1]) ? Integer.MAX_VALUE : Integer.parseInt(card[1]));
    }
    if (profileName.startsWith("#"))
        throw new Exception("blah: " + profileName);
    e.setProfileName(profileName);
    e.setSliceDescription(isProfile ? sheet.getColumn(row, "Slice Description") : "");
    for (String d : discriminator.split("\\,")) if (!Utilities.noString(d))
        e.getDiscriminator().add(d);
    doAliases(sheet, row, e);
    if (sheet.hasColumn(row, "Must Understand"))
        throw new Exception("Column 'Must Understand' has been renamed to 'Is Modifier'");
    if (sheet.hasColumn(row, "Is Modifier")) {
        e.setIsModifier(parseBoolean(sheet.getColumn(row, "Is Modifier"), row, null));
        String reason = sheet.getColumn(row, "Modifier Reason");
        if (Utilities.noString(reason) && e.getName().toLowerCase().contains("status") && sheet.getColumn(row, "Short Name").contains("error"))
            reason = "This element is labelled as a modifier because it is a status element that contains status entered-in-error which means that the resource should not be treated as valid";
        if (Utilities.noString(reason) && e.getName().equals("active"))
            reason = "This element is labelled as a modifier because it is a status element that can indicate that a record should not be treated as valid";
        if (Utilities.noString(reason)) {
            System.out.println("Missing IsModifierReason on " + path);
            reason = "Not known why this is labelled a modifier";
        }
        e.setModifierReason(reason);
    }
    if (isProfile) {
        // later, this will get hooked in from the underlying definitions, but we need to know this now to validate the extension modifier matching
        if (e.getName().equals("modifierExtension"))
            e.setIsModifier(true);
        e.setMustSupport(parseBoolean(sheet.getColumn(row, "Must Support"), row, null));
    }
    if (sheet.hasColumn(row, "Summary"))
        e.setSummaryItem(parseBoolean(sheet.getColumn(row, "Summary"), row, null));
    e.setRegex(sheet.getColumn(row, "Regex"));
    String uml = sheet.getColumn(row, "UML");
    if (uml != null) {
        if (uml.contains(";")) {
            String[] parts = uml.split("\\;");
            e.setSvgLeft(Integer.parseInt(parts[0]));
            e.setSvgTop(Integer.parseInt(parts[1]));
            if (parts.length > 2)
                e.setSvgWidth(Integer.parseInt(parts[2]));
            e.setUmlDir("");
        } else if (uml.startsWith("break:")) {
            e.setUmlBreak(true);
            e.setUmlDir(uml.substring(6));
        } else {
            e.setUmlDir(uml);
        }
    }
    String s = sheet.getColumn(row, "Condition");
    if (s != null && !s.equals(""))
        throw new Exception("Found Condition in spreadsheet " + getLocation(row));
    s = sheet.getColumn(row, "Inv.");
    if (s != null && !s.equals("")) {
        for (String sn : s.split(",")) {
            if (!sn.startsWith("!")) {
                Invariant inv = invariants.get(sn);
                if (inv == null)
                    throw new Exception("unable to find Invariant '" + sn + "' " + getLocation(row));
                e.getStatedInvariants().add(inv);
            }
        }
    }
    TypeParser tp = new TypeParser(version.toCode());
    e.getTypes().addAll(tp.parse(sheet.getColumn(row, "Type"), isProfile, profileExtensionBase, context, !path.contains("."), this.name));
    if (isRoot && e.getTypes().size() == 1 && definitions != null) {
        String t = e.getTypes().get(0).getName();
        if (definitions.getResourceTemplates().containsKey(t)) {
            // we've got a template in play.
            template = definitions.getResourceTemplates().get(t);
            templateTitle = Utilities.unCamelCase(e.getName());
            e.getTypes().get(0).setName(template.getRoot().getTypes().get(0).getName());
        } else if (definitions.getBaseResources().containsKey(t) && definitions.getBaseResources().get(t).isInterface()) {
            // we've got a template in play.
            template = definitions.getBaseResources().get(t);
            templateTitle = Utilities.unCamelCase(e.getName());
        }
    }
    if (isProfile && ((path.endsWith(".extension") || path.endsWith(".modifierExtension")) && (e.getTypes().size() == 1) && e.getTypes().get(0).hasProfile()) && Utilities.noString(profileName))
        throw new Exception("need to have a profile name if a profiled extension is referenced for " + e.getTypes().get(0).getProfile());
    if (sheet.hasColumn(row, "Concept Domain"))
        throw new Exception("Column 'Concept Domain' has been retired in " + path);
    String bindingName = sheet.getColumn(row, "Binding");
    if (!Utilities.noString(bindingName)) {
        BindingSpecification binding = bindings.get(bindingName);
        if (binding == null && definitions != null)
            binding = definitions.getCommonBindings().get(bindingName);
        if (binding == null) {
            if (bindingName.startsWith("!"))
                e.setNoBindingAllowed(true);
            else
                throw new Exception("Binding name " + bindingName + " could not be resolved in local spreadsheet");
        }
        e.setBinding(binding);
        if (binding != null && !binding.getUseContexts().contains(name))
            binding.getUseContexts().add(name);
    } else if (e.getBinding() != null) {
        if (!e.getBinding().getUseContexts().contains(name))
            e.getBinding().getUseContexts().add(name);
    }
    if (!Utilities.noString(sheet.getColumn(row, "Short Label")))
        throw new Exception("Short Label is no longer used");
    if (// todo: make this a warning when a fair chunk of the spreadsheets have been converted
    sheet.hasColumn(row, "Short Name"))
        if (sheet.getColumn(row, "Short Name").startsWith("&"))
            e.setShortDefn(e.getShortDefn() + sheet.getColumn(row, "Short Name").substring(1));
        else
            e.setShortDefn(sheet.getColumn(row, "Short Name"));
    if (!isProfile && e.getShortDefn() == null)
        throw new Exception("A short definition is required for " + e.getName() + " at " + getLocation(row));
    if (sheet.hasColumn(row, "Definition"))
        if (sheet.getColumn(row, "Definition").startsWith("&"))
            e.setDefinition(Utilities.appendPeriod(e.getDefinition() + processDefinition(sheet.getColumn(row, "Definition")).substring(1)));
        else
            e.setDefinition(Utilities.appendPeriod(processDefinition(sheet.getColumn(row, "Definition"))));
    if (isRoot) {
        root.setDefinition(e.getDefinition());
    }
    if (isProfile || isLogicalModel)
        e.setMaxLength(sheet.getColumn(row, "Max Length"));
    if (sheet.hasColumn(row, "Requirements"))
        if (sheet.getColumn(row, "Requirements").startsWith("&"))
            e.setRequirements(Utilities.appendPeriod(e.getRequirements() + sheet.getColumn(row, "Requirements").substring(1)));
        else
            e.setRequirements(Utilities.appendPeriod(sheet.getColumn(row, "Requirements")));
    if (sheet.hasColumn(row, "Comments"))
        if (sheet.getColumn(row, "Comments").startsWith("&"))
            e.setComments(Utilities.appendPeriod(e.getComments() + Utilities.appendPeriod(sheet.getColumn(row, "Comments").substring(1))));
        else
            e.setComments(Utilities.appendPeriod(Utilities.appendPeriod(sheet.getColumn(row, "Comments"))));
    for (String n : mappings.keySet()) {
        String ms = sheet.getColumn(row, mappings.get(n).getColumnName());
        if (mappings.get(n).getColumnName().equals("Snomed Code") && !Utilities.noString(ms))
            System.out.println("!!");
        e.addMapping(n, ms.trim());
    }
    if (pack != null) {
        for (String n : pack.getMappingSpaces().keySet()) {
            e.addMapping(n, sheet.getColumn(row, pack.getMappingSpaces().get(n).getColumnName()).trim());
        }
    }
    if (sheet.hasColumn("Hierarchy"))
        e.setHierarchy(parseBoolean(sheet.getColumn(row, "Hierarchy"), row, null));
    if (sheet.hasColumn(row, "To Do"))
        e.setTodo(Utilities.appendPeriod(sheet.getColumn(row, "To Do")));
    if (sheet.hasColumn(row, "Example"))
        e.setExample(processValue(sheet, row, "Example", sheet.getColumn(row, "Example"), e));
    processOtherExamples(e, sheet, row);
    if (sheet.hasColumn(row, "Committee Notes"))
        e.setCommitteeNotes(Utilities.appendPeriod(sheet.getColumn(row, "Committee Notes")));
    if (sheet.hasColumn(row, "Display Hint"))
        e.setDisplayHint(sheet.getColumn(row, "Display Hint"));
    if (isProfile) {
        e.setFixed(processValue(sheet, row, "Value", sheet.getColumn(row, "Value"), e));
        e.setPattern(processValue(sheet, row, "Pattern", sheet.getColumn(row, "Pattern"), e));
    } else {
        if (sheet.hasColumn(row, "Default Value"))
            errors.add(path + ": Default value '" + sheet.getColumn(row, "Default Value") + "' found @ " + getLocation(row));
        if (sheet.hasColumn(row, "Missing Meaning"))
            e.setMeaningWhenMissing(sheet.getColumn(row, "Missing Meaning"));
    }
    if (sheet.hasColumn(row, "w5"))
        e.setW5(checkW5(sheet.getColumn(row, "w5"), path));
    if (sheet.hasColumn(row, "Translatable"))
        e.setTranslatable(parseBoolean(sheet.getColumn(row, "Translatable"), row, false));
    if (sheet.hasColumn(row, "Order Meaning"))
        e.setOrderMeaning(sheet.getColumn(row, "Order Meaning"));
    return e;
}
Also used : TypeDefn(org.hl7.fhir.definitions.model.TypeDefn) Invariant(org.hl7.fhir.definitions.model.Invariant) TypeParser(org.hl7.fhir.definitions.parsers.TypeParser) ElementDefn(org.hl7.fhir.definitions.model.ElementDefn) BindingSpecification(org.hl7.fhir.definitions.model.BindingSpecification) FHIRException(org.hl7.fhir.exceptions.FHIRException)

Example 20 with Invariant

use of org.hl7.fhir.definitions.model.Invariant in project kindling by HL7.

the class OldSpreadsheetParser method parseLogicalModel.

public LogicalModel parseLogicalModel() throws Exception {
    ResourceDefn resource = new ResourceDefn();
    isLogicalModel = true;
    Sheet sheet = loadSheet("Bindings");
    if (sheet != null)
        readBindings(sheet);
    sheet = loadSheet("Invariants");
    Map<String, Invariant> invariants = null;
    if (sheet != null)
        invariants = readInvariants(sheet, title, "Invariants");
    sheet = loadSheet("Data Elements");
    if (sheet == null)
        throw new Exception("No Sheet found for Data Elements");
    for (int row = 0; row < sheet.rows.size(); row++) {
        processLine(resource, sheet, row, invariants, false, null, row == 0);
    }
    parseMetadata(resource);
    if (invariants != null) {
        for (Invariant inv : invariants.values()) {
            if (Utilities.noString(inv.getContext()))
                throw new Exception("Type " + resource.getRoot().getName() + " Invariant " + inv.getId() + " has no context");
            else {
                ElementDefn ed = findContext(resource.getRoot(), inv.getContext(), "Type " + resource.getRoot().getName() + " Invariant " + inv.getId() + " Context");
                if (ed.getName().endsWith("[x]") && !inv.getContext().endsWith("[x]"))
                    inv.setFixedName(inv.getContext().substring(inv.getContext().lastIndexOf(".") + 1));
                ed.getInvariants().put(inv.getId(), inv);
                if (Utilities.noString(inv.getXpath())) {
                    throw new Exception("Type " + resource.getRoot().getName() + " Invariant " + inv.getId() + " (" + inv.getEnglish() + ") has no XPath statement");
                } else if (inv.getXpath().contains("\""))
                    throw new Exception("Type " + resource.getRoot().getName() + " Invariant " + inv.getId() + " (" + inv.getEnglish() + ") contains a \" character");
            // if (Utilities.noString(inv.getExpression()))
            // throw new Exception("Type "+resource.getRoot().getName()+" Invariant "+inv.getId()+" ("+inv.getEnglish()+") has no Expression statement (in FHIRPath format)");
            }
        }
    }
    // EK: Future types. But those won't get there.
    if (bindings != null)
        resource.getRoot().getNestedBindings().putAll(bindings);
    scanNestedTypes(resource, resource.getRoot(), resource.getName());
    resolveElementReferences(resource, resource.getRoot());
    LogicalModel lm = new LogicalModel();
    lm.setResource(resource);
    lm.setWg(definitions.getWorkgroups().get("fhir"));
    return lm;
}
Also used : Invariant(org.hl7.fhir.definitions.model.Invariant) LogicalModel(org.hl7.fhir.definitions.model.LogicalModel) ElementDefn(org.hl7.fhir.definitions.model.ElementDefn) ResourceDefn(org.hl7.fhir.definitions.model.ResourceDefn) Sheet(org.hl7.fhir.utilities.xls.XLSXmlParser.Sheet) FHIRException(org.hl7.fhir.exceptions.FHIRException)

Aggregations

Invariant (org.hl7.fhir.definitions.model.Invariant)21 ElementDefn (org.hl7.fhir.definitions.model.ElementDefn)11 FHIRException (org.hl7.fhir.exceptions.FHIRException)10 ArrayList (java.util.ArrayList)7 TypeRef (org.hl7.fhir.definitions.model.TypeRef)6 CommaSeparatedStringBuilder (org.hl7.fhir.utilities.CommaSeparatedStringBuilder)6 ElementDefinitionConstraintComponent (org.hl7.fhir.r5.model.ElementDefinition.ElementDefinitionConstraintComponent)5 Sheet (org.hl7.fhir.utilities.xls.XLSXmlParser.Sheet)5 ResourceDefn (org.hl7.fhir.definitions.model.ResourceDefn)4 ElementDefinition (org.hl7.fhir.r5.model.ElementDefinition)4 ProfiledType (org.hl7.fhir.definitions.model.ProfiledType)3 TypeRefComponent (org.hl7.fhir.r5.model.ElementDefinition.TypeRefComponent)3 StringType (org.hl7.fhir.r5.model.StringType)3 BindingSpecification (org.hl7.fhir.definitions.model.BindingSpecification)2 TypeDefn (org.hl7.fhir.definitions.model.TypeDefn)2 FHIRFormatError (org.hl7.fhir.exceptions.FHIRFormatError)2 StructureDefinitionContextComponent (org.hl7.fhir.r5.model.StructureDefinition.StructureDefinitionContextComponent)2 UriType (org.hl7.fhir.r5.model.UriType)2 StandardsStatus (org.hl7.fhir.utilities.StandardsStatus)2 FhirContext (ca.uhn.fhir.context.FhirContext)1