diff --git a/RELEASE_NOTES.md b/RELEASE_NOTES.md index e69de29bb..41328c942 100644 --- a/RELEASE_NOTES.md +++ b/RELEASE_NOTES.md @@ -0,0 +1,5 @@ +* Breaking Change: Fix issue where primitive elements with required bindings must have a value, but this wasn't be checked +* Fix bug with value set imports not working +* Fix bug with base definitions not working properly for logical models +* Better memory tracking for validator +* Get code generator compiling diff --git a/org.hl7.fhir.core.generator/src/org/hl7/fhir/core/generator/tests/RoundTripTests.java b/org.hl7.fhir.core.generator/configuration/tests/RoundTripTests.java similarity index 100% rename from org.hl7.fhir.core.generator/src/org/hl7/fhir/core/generator/tests/RoundTripTests.java rename to org.hl7.fhir.core.generator/configuration/tests/RoundTripTests.java diff --git a/org.hl7.fhir.core.generator/src/org/hl7/fhir/core/generator/codegen/JavaResourceGenerator.java b/org.hl7.fhir.core.generator/src/org/hl7/fhir/core/generator/codegen/JavaResourceGenerator.java index 1b7d6c47e..4458b939e 100644 --- a/org.hl7.fhir.core.generator/src/org/hl7/fhir/core/generator/codegen/JavaResourceGenerator.java +++ b/org.hl7.fhir.core.generator/src/org/hl7/fhir/core/generator/codegen/JavaResourceGenerator.java @@ -996,7 +996,7 @@ private void generatePropertyMaker(Analysis analysis, TypeInfo ti, String indent private List getTypes(List types) { if (types.size() == 1 && types.get(0).getName().equals("*")) { List t = new ArrayList(); - for (String s : TypesUtilities.wildcardTypes()) { + for (String s : TypesUtilities.wildcardTypes("5.0")) { t.add(new TypeRefComponent(s)); } return t; diff --git a/org.hl7.fhir.core.generator/src/org/hl7/fhir/core/generator/engine/DefinitionsLoader.java b/org.hl7.fhir.core.generator/src/org/hl7/fhir/core/generator/engine/DefinitionsLoader.java index eb35204d3..2072038a5 100644 --- a/org.hl7.fhir.core.generator/src/org/hl7/fhir/core/generator/engine/DefinitionsLoader.java +++ b/org.hl7.fhir.core.generator/src/org/hl7/fhir/core/generator/engine/DefinitionsLoader.java @@ -13,8 +13,8 @@ import org.hl7.fhir.r5.model.Resource; import org.hl7.fhir.r5.model.SearchParameter; import org.hl7.fhir.r5.model.StructureDefinition; import org.hl7.fhir.r5.model.ValueSet; -import org.hl7.fhir.utilities.cache.NpmPackage; -import org.hl7.fhir.utilities.cache.ToolsVersion; +import org.hl7.fhir.utilities.npm.NpmPackage; +import org.hl7.fhir.utilities.npm.ToolsVersion; public class DefinitionsLoader { diff --git a/org.hl7.fhir.core.generator/src/org/hl7/fhir/core/generator/engine/JavaCoreGenerator.java b/org.hl7.fhir.core.generator/src/org/hl7/fhir/core/generator/engine/JavaCoreGenerator.java index 543e01cd7..e24a8ac84 100644 --- a/org.hl7.fhir.core.generator/src/org/hl7/fhir/core/generator/engine/JavaCoreGenerator.java +++ b/org.hl7.fhir.core.generator/src/org/hl7/fhir/core/generator/engine/JavaCoreGenerator.java @@ -30,9 +30,9 @@ import org.hl7.fhir.r5.model.SearchParameter; import org.hl7.fhir.r5.model.StructureDefinition; import org.hl7.fhir.utilities.TextFile; import org.hl7.fhir.utilities.Utilities; -import org.hl7.fhir.utilities.cache.FilesystemPackageCacheManager; -import org.hl7.fhir.utilities.cache.NpmPackage; -import org.hl7.fhir.utilities.cache.ToolsVersion; +import org.hl7.fhir.utilities.npm.FilesystemPackageCacheManager; +import org.hl7.fhir.utilities.npm.NpmPackage; +import org.hl7.fhir.utilities.npm.ToolsVersion; public class JavaCoreGenerator { diff --git a/org.hl7.fhir.r5/src/main/java/org/hl7/fhir/r5/conformance/ProfileUtilities.java b/org.hl7.fhir.r5/src/main/java/org/hl7/fhir/r5/conformance/ProfileUtilities.java index 98c00af42..88489aa6c 100644 --- a/org.hl7.fhir.r5/src/main/java/org/hl7/fhir/r5/conformance/ProfileUtilities.java +++ b/org.hl7.fhir.r5/src/main/java/org/hl7/fhir/r5/conformance/ProfileUtilities.java @@ -2989,7 +2989,7 @@ public class ProfileUtilities extends TranslatingUtilities { } if (!ok) { StructureDefinition sdt = context.fetchTypeDefinition(tt); - if (sdt != null && sdt.getAbstract()) { + if (sdt != null && (sdt.getAbstract() || sdt.getKind() == StructureDefinitionKind.LOGICAL)) { StructureDefinition sdb = context.fetchTypeDefinition(t); while (sdb != null && !ok) { ok = sdb.getType().equals(sdt.getType()); diff --git a/org.hl7.fhir.r5/src/main/java/org/hl7/fhir/r5/renderers/ValueSetRenderer.java b/org.hl7.fhir.r5/src/main/java/org/hl7/fhir/r5/renderers/ValueSetRenderer.java index cb0919b01..1bb6904db 100644 --- a/org.hl7.fhir.r5/src/main/java/org/hl7/fhir/r5/renderers/ValueSetRenderer.java +++ b/org.hl7.fhir.r5/src/main/java/org/hl7/fhir/r5/renderers/ValueSetRenderer.java @@ -923,13 +923,21 @@ public class ValueSetRenderer extends TerminologyRenderer { } } else { li.tx("Import all the codes that are contained in "); - boolean first = true; - for (UriType vs : inc.getValueSet()) { - if (first) - first = false; - else - li.tx(", "); - AddVsRef(vs.asStringValue(), li); + if (inc.getValueSet().size() < 4) { + boolean first = true; + for (UriType vs : inc.getValueSet()) { + if (first) + first = false; + else + li.tx(", "); + AddVsRef(vs.asStringValue(), li); + } + } else { + XhtmlNode xul = li.ul(); + for (UriType vs : inc.getValueSet()) { + AddVsRef(vs.asStringValue(), xul.li()); + } + } } return hasExtensions; diff --git a/org.hl7.fhir.r5/src/main/java/org/hl7/fhir/r5/terminologies/ValueSetExpanderSimple.java b/org.hl7.fhir.r5/src/main/java/org/hl7/fhir/r5/terminologies/ValueSetExpanderSimple.java index 0ae49867d..86f0477e3 100644 --- a/org.hl7.fhir.r5/src/main/java/org/hl7/fhir/r5/terminologies/ValueSetExpanderSimple.java +++ b/org.hl7.fhir.r5/src/main/java/org/hl7/fhir/r5/terminologies/ValueSetExpanderSimple.java @@ -510,10 +510,31 @@ public class ValueSetExpanderSimple implements ValueSetExpander { if (!existsInParams(exp.getParameter(), p.getName(), p.getValue())) exp.getParameter().add(p); } + copyExpansion(vso.getValueset().getExpansion().getContains()); canBeHeirarchy = false; // if we're importing a value set, we have to be combining, so we won't try for a heirarchy return vso.getValueset(); } + public void copyExpansion(List list) { + for (ValueSetExpansionContainsComponent cc : list) { + ValueSetExpansionContainsComponent n = new ValueSet.ValueSetExpansionContainsComponent(); + n.setSystem(cc.getSystem()); + n.setCode(cc.getCode()); + n.setAbstract(cc.getAbstract()); + n.setInactive(cc.getInactive()); + n.setDisplay(cc.getDisplay()); + n.getDesignation().addAll(cc.getDesignation()); + + String s = key(n); + if (!map.containsKey(s) && !excludeKeys.contains(s)) { + codes.add(n); + map.put(s, n); + total++; + } + copyExpansion(cc.getContains()); + } + } + private void addErrors(List errs) { for (String s : errs) { if (!allErrors.contains(s)) { diff --git a/org.hl7.fhir.r5/src/main/java/org/hl7/fhir/r5/utils/OperationOutcomeUtilities.java b/org.hl7.fhir.r5/src/main/java/org/hl7/fhir/r5/utils/OperationOutcomeUtilities.java index d273381d4..fc22c8938 100644 --- a/org.hl7.fhir.r5/src/main/java/org/hl7/fhir/r5/utils/OperationOutcomeUtilities.java +++ b/org.hl7.fhir.r5/src/main/java/org/hl7/fhir/r5/utils/OperationOutcomeUtilities.java @@ -54,9 +54,9 @@ public class OperationOutcomeUtilities { issue.addExpression(message.getLocation()); } // pass through line/col if they're present - if (message.getLine() != 0) + if (message.getLine() >= 0) issue.addExtension().setUrl(ToolingExtensions.EXT_ISSUE_LINE).setValue(new IntegerType(message.getLine())); - if (message.getCol() != 0) + if (message.getCol() >= 0) issue.addExtension().setUrl(ToolingExtensions.EXT_ISSUE_COL).setValue(new IntegerType(message.getCol())); issue.setSeverity(convert(message.getLevel())); CodeableConcept c = new CodeableConcept(); diff --git a/org.hl7.fhir.utilities/src/main/java/org/hl7/fhir/utilities/Utilities.java b/org.hl7.fhir.utilities/src/main/java/org/hl7/fhir/utilities/Utilities.java index b4f4f61e6..6eb0ff9bb 100644 --- a/org.hl7.fhir.utilities/src/main/java/org/hl7/fhir/utilities/Utilities.java +++ b/org.hl7.fhir.utilities/src/main/java/org/hl7/fhir/utilities/Utilities.java @@ -1346,6 +1346,21 @@ public class Utilities { return length + BT; } + public static String describeSize(long length) { + if (length < 0) throw new IllegalArgumentException("File length of < 0 passed in..."); + + if (length > Math.pow(ONE_MB, 3)) { + return length / ((long) Math.pow(ONE_MB, 3)) + GB; + } + if (length > Math.pow(ONE_MB, 2)) { + return length / ((long) Math.pow(ONE_MB, 2)) + MB; + } + if (length > ONE_MB) { + return length / (ONE_MB) + KB; + } + return length + BT; + } + public static List splitBytes(byte[] array, byte[] delimiter) { List byteArrays = new LinkedList(); if (delimiter.length == 0) diff --git a/org.hl7.fhir.utilities/src/main/java/org/hl7/fhir/utilities/i18n/I18nConstants.java b/org.hl7.fhir.utilities/src/main/java/org/hl7/fhir/utilities/i18n/I18nConstants.java index 475b1b510..96ac55b96 100644 --- a/org.hl7.fhir.utilities/src/main/java/org/hl7/fhir/utilities/i18n/I18nConstants.java +++ b/org.hl7.fhir.utilities/src/main/java/org/hl7/fhir/utilities/i18n/I18nConstants.java @@ -386,6 +386,7 @@ public class I18nConstants { public static final String TERMINOLOGY_TX_CODE_NOTVALID = "Terminology_TX_Code_NotValid"; public static final String TERMINOLOGY_TX_CODE_UNKNOWN = "Terminology_TX_Code_Unknown"; public static final String TERMINOLOGY_TX_CODE_VALUESET = "Terminology_TX_Code_ValueSet"; + public static final String Terminology_TX_Code_ValueSet_MISSING = "Terminology_TX_Code_ValueSet_MISSING"; public static final String TERMINOLOGY_TX_CODE_VALUESETMAX = "Terminology_TX_Code_ValueSetMax"; public static final String TERMINOLOGY_TX_CODE_VALUESET_EXT = "Terminology_TX_Code_ValueSet_Ext"; public static final String TERMINOLOGY_TX_CODING_COUNT = "Terminology_TX_Coding_Count"; diff --git a/org.hl7.fhir.utilities/src/main/java/org/hl7/fhir/utilities/validation/ValidationMessage.java b/org.hl7.fhir.utilities/src/main/java/org/hl7/fhir/utilities/validation/ValidationMessage.java index 3213c1a33..49e2302d9 100644 --- a/org.hl7.fhir.utilities/src/main/java/org/hl7/fhir/utilities/validation/ValidationMessage.java +++ b/org.hl7.fhir.utilities/src/main/java/org/hl7/fhir/utilities/validation/ValidationMessage.java @@ -164,6 +164,9 @@ public class ValidationMessage implements Comparator, Compara public boolean isError() { return this == FATAL || this == ERROR; } + public boolean isHint() { + return this == INFORMATION; + } } public enum IssueType { diff --git a/org.hl7.fhir.utilities/src/main/resources/Messages.properties b/org.hl7.fhir.utilities/src/main/resources/Messages.properties index 20281b53d..18a850034 100644 --- a/org.hl7.fhir.utilities/src/main/resources/Messages.properties +++ b/org.hl7.fhir.utilities/src/main/resources/Messages.properties @@ -130,6 +130,7 @@ Terminology_TX_Binding_NoSource2 = Binding has no source, so can''t be checked Terminology_TX_Code_NotValid = Code {0} is not a valid code in code system {1} Terminology_TX_Code_Unknown = Unknown Code ({0}#{1}) Terminology_TX_Code_ValueSet = No code provided, and a code is required from the value set {0} ({1}) +Terminology_TX_Code_ValueSet_MISSING = No code provided, and a code is required from the value set Terminology_TX_Code_ValueSetMax = No code provided, and a code must be provided from the value set {0} (max value set {1}) Terminology_TX_Code_ValueSet_Ext = No code provided, and a code should be provided from the value set {0} ({1}) Terminology_TX_Coding_Count = Expected {0} but found {1} coding elements diff --git a/org.hl7.fhir.validation/src/main/java/org/hl7/fhir/validation/ValidatorCli.java b/org.hl7.fhir.validation/src/main/java/org/hl7/fhir/validation/ValidatorCli.java index 4856c2e1c..ad6a160a1 100644 --- a/org.hl7.fhir.validation/src/main/java/org/hl7/fhir/validation/ValidatorCli.java +++ b/org.hl7.fhir.validation/src/main/java/org/hl7/fhir/validation/ValidatorCli.java @@ -61,6 +61,7 @@ POSSIBILITY OF SUCH DAMAGE. import org.hl7.fhir.r5.model.ImplementationGuide; import org.hl7.fhir.r5.model.StructureDefinition; import org.hl7.fhir.utilities.TimeTracker; +import org.hl7.fhir.utilities.Utilities; import org.hl7.fhir.utilities.VersionUtilities; import org.hl7.fhir.validation.cli.model.CliContext; import org.hl7.fhir.validation.cli.services.ComparisonService; @@ -238,6 +239,6 @@ public class ValidatorCli { } break; } - System.out.println("Done. " + tt.report()); + System.out.println("Done. " + tt.report()+". Max Memory = "+Utilities.describeSize(Runtime.getRuntime().maxMemory())); } } \ No newline at end of file diff --git a/org.hl7.fhir.validation/src/main/java/org/hl7/fhir/validation/cli/services/ValidationService.java b/org.hl7.fhir.validation/src/main/java/org/hl7/fhir/validation/cli/services/ValidationService.java index 2aa6bdab4..377ea95ed 100644 --- a/org.hl7.fhir.validation/src/main/java/org/hl7/fhir/validation/cli/services/ValidationService.java +++ b/org.hl7.fhir.validation/src/main/java/org/hl7/fhir/validation/cli/services/ValidationService.java @@ -24,6 +24,8 @@ import org.hl7.fhir.validation.cli.utils.EngineMode; import org.hl7.fhir.validation.cli.utils.VersionSourceInformation; import java.io.FileOutputStream; +import java.lang.management.ManagementFactory; +import java.lang.management.MemoryMXBean; import java.util.ArrayList; import java.util.List; @@ -66,6 +68,7 @@ public class ValidationService { messages.forEach(outcome::addMessage); response.addOutcome(outcome); } + System.out.println(" Max Memory: "+Runtime.getRuntime().maxMemory()); return response; } @@ -87,7 +90,8 @@ public class ValidationService { List records = new ArrayList<>(); Resource r = validator.validate(cliContext.getSources(), cliContext.getProfiles(), records); int ec = 0; - System.out.println("Done. " + validator.getContext().clock().report()); + MemoryMXBean mbean = ManagementFactory.getMemoryMXBean(); + System.out.println("Done. " + validator.getContext().clock().report()+". Memory = "+Utilities.describeSize(mbean.getHeapMemoryUsage().getUsed()+mbean.getNonHeapMemoryUsage().getUsed())); System.out.println(); if (cliContext.getOutput() == null) { @@ -211,7 +215,9 @@ public class ValidationService { public String initializeValidator(CliContext cliContext, String definitions, TimeTracker tt, String sessionId) throws Exception { tt.milestone(); if (!sessionCache.sessionExists(sessionId)) { - System.out.println("No such cached session exists for session id " + sessionId + ", re-instantiating validator."); + if (sessionId != null) { + System.out.println("No such cached session exists for session id " + sessionId + ", re-instantiating validator."); + } System.out.print(" Load FHIR v" + cliContext.getSv() + " from " + definitions); ValidationEngine validator = new ValidationEngine(definitions, cliContext.getSv(), tt); sessionId = sessionCache.cacheSession(validator); diff --git a/org.hl7.fhir.validation/src/main/java/org/hl7/fhir/validation/instance/InstanceValidator.java b/org.hl7.fhir.validation/src/main/java/org/hl7/fhir/validation/instance/InstanceValidator.java index 506704856..a1a8742dc 100644 --- a/org.hl7.fhir.validation/src/main/java/org/hl7/fhir/validation/instance/InstanceValidator.java +++ b/org.hl7.fhir.validation/src/main/java/org/hl7/fhir/validation/instance/InstanceValidator.java @@ -1907,6 +1907,9 @@ public class InstanceValidator extends BaseValidator implements IResourceValidat rule(errors, IssueType.INVALID, e.line(), e.col(), path, e.hasChildren(), I18nConstants.TYPE_SPECIFIC_CHECKS_DT_PRIMITIVE_NOTEMPTY); else if (StringUtils.isWhitespace(e.primitiveValue())) warning(errors, IssueType.INVALID, e.line(), e.col(), path, e.hasChildren(), I18nConstants.TYPE_SPECIFIC_CHECKS_DT_PRIMITIVE_WS); + if (context.hasBinding()) { + rule(errors, IssueType.CODEINVALID, e.line(), e.col(), path, context.getBinding().getStrength() != BindingStrength.REQUIRED, I18nConstants.Terminology_TX_Code_ValueSet_MISSING); + } return; } String regex = context.getExtensionString(ToolingExtensions.EXT_REGEX); diff --git a/pom.xml b/pom.xml index d87015455..e7cb2cc24 100644 --- a/pom.xml +++ b/pom.xml @@ -19,7 +19,7 @@ 5.1.0 - 1.1.59 + 1.1.60-SNAPSHOT 5.7.1 1.7.1 3.0.0-M4