use of org.hl7.fhir.r4.model.ElementDefinition in project org.hl7.fhir.core by hapifhir.
the class ShExGenerator method genTypeRef.
/**
* Generate a type reference
* @param sd Containing structure definition
* @param ed Containing element definition
* @param id Element id
* @param typ Element type
* @return Type reference string
*/
private String genTypeRef(StructureDefinition sd, ElementDefinition ed, String id, ElementDefinition.TypeRefComponent typ) {
if (typ.hasProfile()) {
if (typ.getCode().equals("Reference"))
return genReference("", typ);
else if (ProfileUtilities.getChildList(sd, ed).size() > 0) {
// inline anonymous type - give it a name and factor it out
innerTypes.add(new ImmutablePair<StructureDefinition, ElementDefinition>(sd, ed));
return simpleElement(sd, ed, id);
} else {
String ref = getTypeName(typ);
datatypes.add(ref);
return simpleElement(sd, ed, ref);
}
} else if (typ.getCodeElement().getExtensionsByUrl(ToolingExtensions.EXT_RDF_TYPE).size() > 0) {
String xt = null;
try {
xt = typ.getCodeElement().getExtensionString(ToolingExtensions.EXT_RDF_TYPE);
} catch (FHIRException e) {
e.printStackTrace();
}
// TODO: Remove the next line when the type of token gets switched to string
// TODO: Add a rdf-type entry for valueInteger to xsd:integer (instead of int)
ST td_entry = tmplt(PRIMITIVE_ELEMENT_DEFN_TEMPLATE).add("typ", xt.replace("xsd:token", "xsd:string").replace("xsd:int", "xsd:integer"));
StringBuilder facets = new StringBuilder();
if (ed.hasMinValue()) {
Type mv = ed.getMinValue();
facets.append(tmplt(MINVALUE_TEMPLATE).add("val", TurtleParser.ttlLiteral(mv.primitiveValue(), mv.fhirType())).render());
}
if (ed.hasMaxValue()) {
Type mv = ed.getMaxValue();
facets.append(tmplt(MAXVALUE_TEMPLATE).add("val", TurtleParser.ttlLiteral(mv.primitiveValue(), mv.fhirType())).render());
}
if (ed.hasMaxLength()) {
int ml = ed.getMaxLength();
facets.append(tmplt(MAXLENGTH_TEMPLATE).add("val", ml).render());
}
if (ed.hasPattern()) {
Type pat = ed.getPattern();
facets.append(tmplt(PATTERN_TEMPLATE).add("val", pat.primitiveValue()).render());
}
td_entry.add("facets", facets.toString());
return td_entry.render();
} else if (typ.getCode() == null) {
ST primitive_entry = tmplt(PRIMITIVE_ELEMENT_DEFN_TEMPLATE);
primitive_entry.add("typ", "xsd:string");
return primitive_entry.render();
} else if (typ.getCode().equals("xhtml")) {
return tmplt(XHTML_TYPE_TEMPLATE).render();
} else {
datatypes.add(typ.getCode());
return simpleElement(sd, ed, typ.getCode());
}
}
use of org.hl7.fhir.r4.model.ElementDefinition in project org.hl7.fhir.core by hapifhir.
the class ShExGenerator method genShapeDefinition.
/**
* Emit a ShEx definition for the supplied StructureDefinition
* @param sd Structure definition to emit
* @param top_level True means outermost type, False means recursively called
* @return ShEx definition
*/
private String genShapeDefinition(StructureDefinition sd, boolean top_level) {
// xhtml is treated as an atom
if ("xhtml".equals(sd.getName()) || (completeModel && "Resource".equals(sd.getName())))
return "";
ST shape_defn;
// Resources are either incomplete items or consist of everything that is defined as a resource (completeModel)
if ("Resource".equals(sd.getName())) {
shape_defn = tmplt(RESOURCE_SHAPE_TEMPLATE);
known_resources.add(sd.getName());
} else {
shape_defn = tmplt(SHAPE_DEFINITION_TEMPLATE).add("id", sd.getId());
if (sd.getKind().equals(StructureDefinition.StructureDefinitionKind.RESOURCE)) {
// || sd.getKind().equals(StructureDefinition.StructureDefinitionKind.COMPLEXTYPE)) {
known_resources.add(sd.getName());
ST resource_decl = tmplt(RESOURCE_DECL_TEMPLATE).add("id", sd.getId()).add("root", tmplt(ROOT_TEMPLATE));
// add("root", top_level ? tmplt(ROOT_TEMPLATE) : "");
shape_defn.add("resourceDecl", resource_decl.render());
} else {
shape_defn.add("resourceDecl", "");
}
}
// Generate the defining elements
List<String> elements = new ArrayList<String>();
// Add the additional entries for special types
String sdn = sd.getName();
if (sdn.equals("Coding"))
elements.add(tmplt(CONCEPT_REFERENCE_TEMPLATE).render());
else if (sdn.equals("CodeableConcept"))
elements.add(tmplt(CONCEPT_REFERENCES_TEMPLATE).render());
else if (sdn.equals("Reference"))
elements.add(tmplt(RESOURCE_LINK_TEMPLATE).render());
// else if (sdn.equals("Extension"))
// return tmplt(EXTENSION_TEMPLATE).render();
String root_comment = null;
for (ElementDefinition ed : sd.getSnapshot().getElement()) {
if (!ed.getPath().contains("."))
root_comment = ed.getShort();
else if (StringUtils.countMatches(ed.getPath(), ".") == 1 && !"0".equals(ed.getMax())) {
elements.add(genElementDefinition(sd, ed));
}
}
shape_defn.add("elements", StringUtils.join(elements, "\n"));
shape_defn.add("comment", root_comment == null ? " " : "# " + root_comment);
return shape_defn.render();
}
use of org.hl7.fhir.r4.model.ElementDefinition in project org.hl7.fhir.core by hapifhir.
the class ShExGenerator method simpleElement.
/**
* Generate a type reference and optional value set definition
* @param sd Containing StructureDefinition
* @param ed Element being defined
* @param typ Element type
* @return Type definition
*/
private String simpleElement(StructureDefinition sd, ElementDefinition ed, String typ) {
String addldef = "";
ElementDefinition.ElementDefinitionBindingComponent binding = ed.getBinding();
if (binding.hasStrength() && binding.getStrength() == Enumerations.BindingStrength.REQUIRED && "code".equals(typ)) {
ValueSet vs = resolveBindingReference(sd, binding.getValueSet());
if (vs != null) {
addldef = tmplt(VALUESET_DEFN_TEMPLATE).add("vsn", vsprefix(vs.getUrl())).render();
required_value_sets.add(vs);
}
}
// TODO: check whether value sets and fixed are mutually exclusive
if (ed.hasFixed()) {
addldef = tmplt(FIXED_VALUE_TEMPLATE).add("val", ed.getFixed().primitiveValue()).render();
}
return tmplt(SIMPLE_ELEMENT_DEFN_TEMPLATE).add("typ", typ).add("vsdef", addldef).render();
}
use of org.hl7.fhir.r4.model.ElementDefinition in project org.hl7.fhir.core by hapifhir.
the class ProfileUtilities method genElement.
private void genElement(String defPath, HierarchicalTableGenerator gen, List<Row> rows, ElementDefinition element, List<ElementDefinition> all, List<StructureDefinition> profiles, boolean showMissing, String profileBaseFileName, Boolean extensions, boolean snapshot, String corePath, String imagePath, boolean root, boolean logicalModel, boolean isConstraintMode, boolean allInvariants) throws IOException {
StructureDefinition profile = profiles == null ? null : profiles.get(profiles.size() - 1);
String s = tail(element.getPath());
List<ElementDefinition> children = getChildren(all, element);
boolean isExtension = (s.equals("extension") || s.equals("modifierExtension"));
if (!snapshot && isExtension && extensions != null && extensions != isExtension)
return;
if (!onlyInformationIsMapping(all, element)) {
Row row = gen.new Row();
row.setAnchor(element.getPath());
row.setColor(getRowColor(element, isConstraintMode));
boolean hasDef = element != null;
boolean ext = false;
if (s.equals("extension")) {
if (element.hasType() && element.getType().get(0).hasProfile() && extensionIsComplex(element.getType().get(0).getProfile()))
row.setIcon("icon_extension_complex.png", HierarchicalTableGenerator.TEXT_ICON_EXTENSION_COMPLEX);
else
row.setIcon("icon_extension_simple.png", HierarchicalTableGenerator.TEXT_ICON_EXTENSION_SIMPLE);
ext = true;
} else if (s.equals("modifierExtension")) {
if (element.hasType() && element.getType().get(0).hasProfile() && extensionIsComplex(element.getType().get(0).getProfile()))
row.setIcon("icon_modifier_extension_complex.png", HierarchicalTableGenerator.TEXT_ICON_EXTENSION_COMPLEX);
else
row.setIcon("icon_modifier_extension_simple.png", HierarchicalTableGenerator.TEXT_ICON_EXTENSION_SIMPLE);
} else if (!hasDef || element.getType().size() == 0)
row.setIcon("icon_element.gif", HierarchicalTableGenerator.TEXT_ICON_ELEMENT);
else if (hasDef && element.getType().size() > 1) {
if (allTypesAre(element.getType(), "Reference"))
row.setIcon("icon_reference.png", HierarchicalTableGenerator.TEXT_ICON_REFERENCE);
else
row.setIcon("icon_choice.gif", HierarchicalTableGenerator.TEXT_ICON_CHOICE);
} else if (hasDef && element.getType().get(0).getCode() != null && element.getType().get(0).getCode().startsWith("@"))
row.setIcon("icon_reuse.png", HierarchicalTableGenerator.TEXT_ICON_REUSE);
else if (hasDef && isPrimitive(element.getType().get(0).getCode()))
row.setIcon("icon_primitive.png", HierarchicalTableGenerator.TEXT_ICON_PRIMITIVE);
else if (hasDef && isReference(element.getType().get(0).getCode()))
row.setIcon("icon_reference.png", HierarchicalTableGenerator.TEXT_ICON_REFERENCE);
else if (hasDef && isDataType(element.getType().get(0).getCode()))
row.setIcon("icon_datatype.gif", HierarchicalTableGenerator.TEXT_ICON_DATATYPE);
else
row.setIcon("icon_resource.png", HierarchicalTableGenerator.TEXT_ICON_RESOURCE);
String ref = defPath == null ? null : defPath + element.getId();
UnusedTracker used = new UnusedTracker();
used.used = true;
Cell left = gen.new Cell(null, ref, s, (element.hasSliceName() ? translate("sd.table", "Slice") + " " + element.getSliceName() : "") + (hasDef && element.hasSliceName() ? ": " : "") + (!hasDef ? null : gt(element.getDefinitionElement())), null);
row.getCells().add(left);
Cell gc = gen.new Cell();
row.getCells().add(gc);
if (element != null && element.getIsModifier())
checkForNoChange(element.getIsModifierElement(), gc.addStyledText(translate("sd.table", "This element is a modifier element"), "?!", null, null, null, false));
if (element != null && element.getMustSupport())
checkForNoChange(element.getMustSupportElement(), gc.addStyledText(translate("sd.table", "This element must be supported"), "S", "white", "red", null, false));
if (element != null && element.getIsSummary())
checkForNoChange(element.getIsSummaryElement(), gc.addStyledText(translate("sd.table", "This element is included in summaries"), "\u03A3", null, null, null, false));
if (element != null && (!element.getConstraint().isEmpty() || !element.getCondition().isEmpty()))
gc.addStyledText(translate("sd.table", "This element has or is affected by some invariants"), "I", null, null, null, false);
ExtensionContext extDefn = null;
if (ext) {
if (element != null && element.getType().size() == 1 && element.getType().get(0).hasProfile()) {
extDefn = locateExtension(StructureDefinition.class, element.getType().get(0).getProfile());
if (extDefn == null) {
genCardinality(gen, element, row, hasDef, used, null);
row.getCells().add(gen.new Cell(null, null, "?? " + element.getType().get(0).getProfile(), null, null));
generateDescription(gen, row, element, null, used.used, profile.getUrl(), element.getType().get(0).getProfile(), profile, corePath, imagePath, root, logicalModel, allInvariants);
} else {
String name = urltail(element.getType().get(0).getProfile());
left.getPieces().get(0).setText(name);
// left.getPieces().get(0).setReference((String) extDefn.getExtensionStructure().getTag("filename"));
left.getPieces().get(0).setHint(translate("sd.table", "Extension URL") + " = " + extDefn.getUrl());
genCardinality(gen, element, row, hasDef, used, extDefn.getElement());
ElementDefinition valueDefn = extDefn.getExtensionValueDefinition();
if (valueDefn != null && !"0".equals(valueDefn.getMax()))
genTypes(gen, row, valueDefn, profileBaseFileName, profile, corePath, imagePath);
else
// if it's complex, we just call it nothing
// genTypes(gen, row, extDefn.getSnapshot().getElement().get(0), profileBaseFileName, profile);
row.getCells().add(gen.new Cell(null, null, "(" + translate("sd.table", "Complex") + ")", null, null));
generateDescription(gen, row, element, extDefn.getElement(), used.used, null, extDefn.getUrl(), profile, corePath, imagePath, root, logicalModel, allInvariants, valueDefn);
}
} else {
genCardinality(gen, element, row, hasDef, used, null);
if ("0".equals(element.getMax()))
row.getCells().add(gen.new Cell());
else
genTypes(gen, row, element, profileBaseFileName, profile, corePath, imagePath);
generateDescription(gen, row, element, null, used.used, null, null, profile, corePath, imagePath, root, logicalModel, allInvariants);
}
} else {
genCardinality(gen, element, row, hasDef, used, null);
if (hasDef && !"0".equals(element.getMax()))
genTypes(gen, row, element, profileBaseFileName, profile, corePath, imagePath);
else
row.getCells().add(gen.new Cell());
generateDescription(gen, row, element, null, used.used, null, null, profile, corePath, imagePath, root, logicalModel, allInvariants);
}
if (element.hasSlicing()) {
if (standardExtensionSlicing(element)) {
used.used = element.hasType() && element.getType().get(0).hasProfile();
showMissing = false;
} else {
row.setIcon("icon_slice.png", HierarchicalTableGenerator.TEXT_ICON_SLICE);
row.getCells().get(2).getPieces().clear();
for (Cell cell : row.getCells()) for (Piece p : cell.getPieces()) {
p.addStyle("font-style: italic");
}
}
}
if (used.used || showMissing)
rows.add(row);
if (!used.used && !element.hasSlicing()) {
for (Cell cell : row.getCells()) for (Piece p : cell.getPieces()) {
p.setStyle("text-decoration:line-through");
p.setReference(null);
}
} else {
for (ElementDefinition child : children) if (logicalModel || !child.getPath().endsWith(".id") || (child.getPath().endsWith(".id") && (profile != null) && (profile.getDerivation() == TypeDerivationRule.CONSTRAINT)))
genElement(defPath, gen, row.getSubRows(), child, all, profiles, showMissing, profileBaseFileName, isExtension, snapshot, corePath, imagePath, false, logicalModel, isConstraintMode, allInvariants);
if (!snapshot && (extensions == null || !extensions))
for (ElementDefinition child : children) if (child.getPath().endsWith(".extension") || child.getPath().endsWith(".modifierExtension"))
genElement(defPath, gen, row.getSubRows(), child, all, profiles, showMissing, profileBaseFileName, true, false, corePath, imagePath, false, logicalModel, isConstraintMode, allInvariants);
}
}
}
use of org.hl7.fhir.r4.model.ElementDefinition in project org.hl7.fhir.core by hapifhir.
the class ProfileUtilities method sliceSummary.
private String sliceSummary(ElementDefinition ed) {
if (!ed.hasSlicing() && !ed.hasSliceName())
return "";
if (ed.hasSliceName())
return " (slicename = " + ed.getSliceName() + ")";
StringBuilder b = new StringBuilder();
boolean first = true;
for (ElementDefinitionSlicingDiscriminatorComponent d : ed.getSlicing().getDiscriminator()) {
if (first)
first = false;
else
b.append("|");
b.append(d.getPath());
}
return " (slicing by " + b.toString() + ")";
}
Aggregations