[YANGTOOLS-1542] Improve YangInstanceIdentifier serialization error reporting Created: 22/Sep/23  Updated: 02/Oct/23  Resolved: 02/Oct/23

Status: Resolved
Project: yangtools
Component/s: codecs
Affects Version/s: None
Fix Version/s: 9.0.9, 10.0.10, 11.0.3

Type: Improvement Priority: Medium
Reporter: Robert Varga Assignee: Robert Varga
Resolution: Done Votes: 0
Labels: pt
Remaining Estimate: Not Specified
Time Spent: Not Specified
Original Estimate: Not Specified

Issue Links:
Relates
relates to NETCONF-1130 (devices) POST returns 500 on data al... Resolved

 Description   

NETCONF-1130 contains this stack trace:

2023-09-05T12:38:46,308 | ERROR | qtp1936609051-682 | ServerRuntime$Responder          | 172 - org.glassfish.jersey.core.jersey-server - 2.40.0 | An exception has been thrown from an exception mapper class org.opendaylight.restconf.nb.rfc8040.jersey.providers.errors.RestconfDocumentedExceptionMapper.
java.lang.IllegalArgumentException: Invalid input /(http://netconfcentral.org/ns/toaster2?revision=2009-11-20)toaster/darknessFactor: schema for argument (http://netconfcentral.org/ns/toaster2?revision=2009-11-20)toaster (after ) not found
	at com.google.common.base.Preconditions.checkArgument(Preconditions.java:463) ~[bundleFile:?]
	at org.opendaylight.yangtools.yang.data.util.AbstractStringInstanceIdentifierCodec.serializeImpl(AbstractStringInstanceIdentifierCodec.java:53) ~[bundleFile:?]
	at org.opendaylight.yangtools.yang.data.util.AbstractStringInstanceIdentifierCodec.serializeImpl(AbstractStringInstanceIdentifierCodec.java:35) ~[bundleFile:?]
	at org.opendaylight.yangtools.yang.data.api.codec.AbstractIllegalArgumentCodec.serialize(AbstractIllegalArgumentCodec.java:32) ~[?:?]
	at org.opendaylight.yangtools.yang.data.codec.gson.JSONInstanceIdentifierCodec.writeValue(JSONInstanceIdentifierCodec.java:107) ~[bundleFile:?]
	at org.opendaylight.yangtools.yang.data.codec.gson.JSONInstanceIdentifierCodec$RFC7951.writeValue(JSONInstanceIdentifierCodec.java:37) ~[bundleFile:?]
	at org.opendaylight.yangtools.yang.data.codec.gson.JSONNormalizedNodeStreamWriter.writeValue(JSONNormalizedNodeStreamWriter.java:459) ~[bundleFile:?]
	at org.opendaylight.yangtools.yang.data.codec.gson.JSONNormalizedNodeStreamWriter.scalarValue(JSONNormalizedNodeStreamWriter.java:441) ~[bundleFile:?]
	at org.opendaylight.yangtools.yang.data.api.schema.stream.ForwardingNormalizedNodeStreamWriter.scalarValue(ForwardingNormalizedNodeStreamWriter.java:107) ~[bundleFile:?]
	at org.opendaylight.restconf.nb.rfc8040.jersey.providers.errors.StreamWriterWithDisabledValidation.scalarValue(StreamWriterWithDisabledValidation.java:50) ~[bundleFile:?]
	at org.opendaylight.yangtools.yang.data.api.schema.stream.NormalizedNodeWriter.wasProcessAsSimpleNode(NormalizedNodeWriter.java:129) ~[bundleFile:?]
	at org.opendaylight.yangtools.yang.data.api.schema.stream.NormalizedNodeWriter.write(NormalizedNodeWriter.java:103) ~[bundleFile:?]
	at org.opendaylight.yangtools.yang.data.api.schema.stream.NormalizedNodeWriter.writeChildren(NormalizedNodeWriter.java:170) ~[bundleFile:?]
	at org.opendaylight.yangtools.yang.data.api.schema.stream.NormalizedNodeWriter.wasProcessedAsCompositeNode(NormalizedNodeWriter.java:190) ~[bundleFile:?]
	at org.opendaylight.yangtools.yang.data.api.schema.stream.NormalizedNodeWriter.write(NormalizedNodeWriter.java:99) ~[bundleFile:?]
	at org.opendaylight.yangtools.yang.data.api.schema.stream.NormalizedNodeWriter.writeChildren(NormalizedNodeWriter.java:170) ~[bundleFile:?]
	at org.opendaylight.yangtools.yang.data.api.schema.stream.NormalizedNodeWriter.wasProcessedAsCompositeNode(NormalizedNodeWriter.java:196) ~[bundleFile:?]
	at org.opendaylight.yangtools.yang.data.api.schema.stream.NormalizedNodeWriter.write(NormalizedNodeWriter.java:99) ~[bundleFile:?]
	at org.opendaylight.yangtools.yang.data.api.schema.stream.NormalizedNodeWriter.writeChildren(NormalizedNodeWriter.java:170) ~[bundleFile:?]
	at org.opendaylight.yangtools.yang.data.api.schema.stream.NormalizedNodeWriter.wasProcessedAsCompositeNode(NormalizedNodeWriter.java:185) ~[bundleFile:?]
	at org.opendaylight.yangtools.yang.data.api.schema.stream.NormalizedNodeWriter.write(NormalizedNodeWriter.java:99) ~[bundleFile:?]
	at org.opendaylight.restconf.nb.rfc8040.jersey.providers.errors.RestconfDocumentedExceptionMapper.writeNormalizedNode(RestconfDocumentedExceptionMapper.java:198) ~[bundleFile:?]

The (perhaps cosmetic) problem here is that we are in NormalizedNodeWriter.write(), which is declared to throw IOException (in this case).

This turns out to be a specific problem of YangInstanceIdentifier codecs in both JSON and XML (where we should report an XMLStreamException). Both of these call sites are serviced by AbstractIllegalArgumentCodec.serialize() which, as the class name would suggest, throws IllegalArgumentException.

This means that writeValue() should first serialize the value safely:

    final String str;
    try {
         str = serialize(iid);
    } catch (IllegalArgumentException e) {
         throw new IOException(e);
    }

and emit it separately. This will allow this case to be properly serviced by RestconfDocumentedExceptionMapper.writeNormalizedNode(), if ever possible.


Generated at Wed Feb 07 20:56:27 UTC 2024 using Jira 8.20.10#820010-sha1:ace47f9899e9ee25d7157d59aa17ab06aee30d3d.