Fix duplicate removal code that caused missed WARNING messages (#1698)

* Fix equality method that caused missed WARNING messages

* Fix logic so that messages get replaced with higher severity if found

* Fix test
This commit is contained in:
dotasek 2024-07-30 11:52:20 -04:00 committed by GitHub
parent f30150ff4b
commit 673950f9d5
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
3 changed files with 32 additions and 8 deletions

View File

@ -757,7 +757,9 @@ public class ValidationMessage implements Comparator<ValidationMessage>, Compara
@Override
public boolean equals(Object o) {
return (this.getMessage() != null && this.getMessage().equals(((ValidationMessage)o).getMessage())) && (this.getLocation() != null && this.getLocation().equals(((ValidationMessage)o).getLocation()));
return (
this.getMessage() != null && this.getMessage().equals(((ValidationMessage)o).getMessage()))
&& (this.getLocation() != null && this.getLocation().equals(((ValidationMessage)o).getLocation()));
}
@Override

View File

@ -5608,6 +5608,31 @@ public class InstanceValidator extends BaseValidator implements IResourceValidat
}
}
private static void addMessagesReplaceExistingIfMoreSevere(List<ValidationMessage> errors, List<ValidationMessage> newErrors) {
for (ValidationMessage newError : newErrors) {
int index = indexOfMatchingMessageAndLocation(errors, newError);
if (index == -1) {
errors.add(newError);
} else {
ValidationMessage existingError = errors.get(index);
if (newError.getLevel().ordinal() < existingError.getLevel().ordinal()) {
errors.set(index, newError);
}
}
}
}
private static int indexOfMatchingMessageAndLocation(List<ValidationMessage> messages, ValidationMessage message) {
for (int i = 0; i < messages.size(); i++) {
ValidationMessage iMessage = messages.get(i);
if (message.getMessage() != null && message.getMessage().equals(iMessage.getMessage())
&& message.getLocation() != null && message.getLocation().equals(iMessage.getLocation())) {
return i;
}
}
return -1;
}
public boolean startInner(ValidationContext valContext, List<ValidationMessage> errors, Element resource, Element element, StructureDefinition defn, NodeStack stack, boolean checkSpecials, PercentageTracker pct, ValidationMode mode, boolean fromContained) {
// the first piece of business is to see if we've validated this resource against this profile before.
// if we have (*or if we still are*), then we'll just return our existing errors
@ -5629,11 +5654,7 @@ public class InstanceValidator extends BaseValidator implements IResourceValidat
trackUsage(defn, valContext, element);
ok = validateElement(valContext, localErrors, defn, defn.getSnapshot().getElement().get(0), null, null, resource, element, element.getName(), stack, false, true, null, pct, mode) && ok;
resTracker.storeOutcomes(defn, localErrors);
for (ValidationMessage vm : localErrors) {
if (!errors.contains(vm)) {
errors.add(vm);
}
}
addMessagesReplaceExistingIfMoreSevere(errors, localErrors);
} else {
ok = false;
}

View File

@ -283,12 +283,13 @@ public class ValidationEngineTests {
OperationOutcome op = ve.validate(FhirFormat.JSON, TestingUtilities.loadTestResourceStream("validator", "observation401_ucum.json"), profiles);
Assertions.assertTrue(checkOutcomes("test401USCore", op,
"Observation null information/informational: Validate Observation against the Body weight profile (http://hl7.org/fhir/StructureDefinition/bodyweight) which is required by the FHIR specification because the LOINC code 29463-7 was found\n"+
"Observation.code.coding[0].system null information/not-found: A definition for CodeSystem 'http://loinc.org' could not be found, so the code cannot be validated\n"+
"Observation.value.ofType(Quantity) null warning/business-rule: Unable to validate code 'kg' in system 'http://unitsofmeasure.org' because the validator is running without terminology services\n"+
"Observation.value.ofType(Quantity).code null warning/informational: Unable to validate code without using server because: Resolved system http://unitsofmeasure.org (v3.0.1), but the definition doesn't include any codes, so the code has not been validated\n"+
// "Observation.code null warning/code-invalid: None of the codings provided are in the value set 'Vital Signs' (http://hl7.org/fhir/ValueSet/observation-vitalsignresult|4.0.1), and a coding should come from this value set unless it has no suitable code (note that the validator cannot judge what is suitable) (codes = http://loinc.org#29463-7)\n"+
"Observation null warning/invalid: Best Practice Recommendation: In general, all observations should have a performer\n"+
"Observation.code null warning/not-found: Unable to check whether the code is in the value set 'http://hl7.org/fhir/ValueSet/observation-vitalsignresult|4.0.1' because the code system http://loinc.org was not found\n"+
"Observation.code.coding[0].system null warning/not-found: A definition for CodeSystem 'http://loinc.org' could not be found, so the code cannot be validated\n"+
"Observation.code null warning/not-found: Unable to check whether the code is in the value set 'http://hl7.org/fhir/ValueSet/observation-vitalsignresult|4.0.1' because the code system http://loinc.org was not found\n"+
"Observation null warning/invariant: Constraint failed: dom-6: 'A resource should have narrative for robust management' (defined in http://hl7.org/fhir/StructureDefinition/DomainResource) (Best Practice Recommendation)"));
assertTrue(logger.verifyHasNoRequests(), "Unexpected request to TX server");
}