json-schema-validator icon indicating copy to clipboard operation
json-schema-validator copied to clipboard

The error message of keyword oneOf,anyOf,allOf is not enough clear.

Open rabbitloveLHF opened this issue 3 years ago • 4 comments

When I recently tested the combination keywords oneOf、anyOf and allOf, I found that they didn't report errors as well as I understood them. I looked at the source code and found that this is related to the implementation of the source code. The version is 1.0.59.

OneOfValidator issue: The numberOfValidSchema <1 logic also need report error message like numberOfValidSchema > 1,It also need a process just like "getMultiSchemasValidErrorMsg(at)" did.

// ensure there is always an "OneOf" error reported if number of valid schemas is not equal to 1.
if (numberOfValidSchema > 1) {
    // check if the parent schema declares the fields as nullable
    if (!JsonType.NULL.equals(TypeFactory.getValueNodeType(node, this.validationContext.getConfig())) ||
            !JsonNodeUtil.isNodeNullable(parentSchema.getSchemaNode(), this.validationContext.getConfig()) &&
                    !JsonNodeUtil.isChildNodeNullable((ArrayNode) schemaNode, this.validationContext.getConfig())) {
        final ValidationMessage message = getMultiSchemasValidErrorMsg(at);
        if (failFast) {
            throw new JsonSchemaException(message);
        }
        errors.add(message);
    }
}
// ensure there is always an "OneOf" error reported if number of valid schemas is not equal to 1.
else if (numberOfValidSchema < 1) {
    if (!childErrors.isEmpty()) {
        errors.addAll(childErrors);
    }
    if( failFast ){
        throw new JsonSchemaException(errors.toString());
    }
}
private ValidationMessage getMultiSchemasValidErrorMsg(String at){
    String msg="";
    for(ShortcutValidator schema: schemas){
        String schemaValue = schema.getSchema().getSchemaNode().toString();
        msg = msg.concat(schemaValue);
    }

    return ValidationMessage.of(getValidatorType().getValue(), ValidatorTypeCode.ONE_OF ,
                                at, String.format("but more than one schemas {%s} are valid ",msg));
}

Howerver,I think the class AllOfValidator and AnyOfValidator also need the error message process just like getting the keyword related error message in the "jsv-message" Resource Bundle. But the current implementation doesn't use the error message just add the child schema errors into error set and report them. I wish you could have given a more friendly error message to make it easier for users to understand that this is an error for a combined schema, not just a single subschema.

rabbitloveLHF avatar Feb 25 '22 02:02 rabbitloveLHF

@rabbitloveLHF I totally agree with you and we have an issue still open to address the error messages. When validators are part of oneOf, allOf or anyOf, the validation message should be a combination of subschema and the context. I am wondering if you could submit a PR to get it fixed. Thanks a lot for raising it.

stevehu avatar Feb 25 '22 05:02 stevehu

@stevehu I can try to do that, but it might take some time.

rabbitloveLHF avatar Mar 04 '22 09:03 rabbitloveLHF

@stevehu I have created a PR for you.

rabbitloveLHF avatar Mar 30 '22 08:03 rabbitloveLHF

I solved the problem to some extent, but it wasn't perfect. For example, I think the error report for OneOfValidator should be like this: image image

But it need to change the data model of error message,we need more time to optimize it.

rabbitloveLHF avatar Mar 30 '22 08:03 rabbitloveLHF

Resolved in #543

fdutton avatar May 23 '23 01:05 fdutton