New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Improve location information in JsonReader exception messages #1764
Open
Marcono1234
wants to merge
13
commits into
google:main
Choose a base branch
from
Marcono1234:marcono1234/exception-message-incorrect-position
base: main
Could not load branches
Branch not found: {{ refName }}
Could not load tags
Nothing to show
Are you sure you want to change the base?
Some commits from the old base branch may be removed from the timeline,
and old review comments may become outdated.
Open
Improve location information in JsonReader exception messages #1764
Marcono1234
wants to merge
13
commits into
google:main
from
Marcono1234:marcono1234/exception-message-incorrect-position
Conversation
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Previously JsonReader.doPeek() would have already advanced or modified the state of the reader when malformed JSON was encountered and an exception was thrown. Therefore repeatedly calling methods which peek would result in inconsistent exceptions and could even make the JSON "valid" again by simply advancing past the malformed JSON. Now the state of the reader is only modified when valid JSON is encountered. Note that there are a few remaining cases where this issue still occurs, which will be fixed in subsequent commits. This change required adding more JsconScope constants because if there is enough space (or a long comment) between tokens the skipped content could not have been stored in the buffer, e.g. `{"a": ... :1}`. Here a value is expected after the `:`. However there are a lot of whitespaces followed by a second `:` (i.e. malformed JSON). With the previous JsonScopes it would not have been possible to represent this state correctly. Therefore a subsequent peek would have consumed the second `:` making the JSON "valid" again.
…scape Previously JsonReader.nextString() and skipValue() consumed the '\' of an escape sequence before throwing an exception for invalid escape sequences. Therefore a subsequent method call would have read a "valid" string. Now the stream position is only advanced when the escape sequence is valid.
Check for exception messages and make caught exception type more specific in some cases to make sure tests do not catch wrong exception and erroneously assume that code works as expected. Removes JsonWriterTest.testStrictWriterDoesNotPermitMultipleTopLevelValues() because it is the same as testMultipleTopLevelValues().
For a malformed unicode escape sequence the exception message thrown be the method erroneously only included the first 4 chars which is `\uXX`, missing the last 2 hex chars.
…ion-message-incorrect-position
Previously when JsonReader threw an exception describing an issue with the peeked value (e.g. it being different than the expected one) it used the current `lineNumber` and `pos`. This resulted in confusing error messages because both values point behind the value responsible for the error. For example: new JsonReader(new StringReader("true")).beginObject(); // Expected BEGIN_OBJECT but was BOOLEAN at line 1 column 5 path $ With these changes the exception messages now correctly refer to the start of the peeked value.
Adds location information to some exceptions thrown by JsonReader which previously did not have any location information.
Previously JsonReader threw an exception when a number or keyword was followed by a lenient non-literal. This made JsonReader consider the complete number / keyword malformed even though only the separator is malformed. To be consistent with EOF exceptions and exceptions for string values, the exception is now only thrown after the number / keyword has been consumed and when the caller tries to peek at the next JSON token. For example: JsonReader reader = new JsonReader(new StringReader("[true;true]")); reader.beginArray(); // Would previously already have thrown exception; with these changes // only trying to read value after that will throw exception reader.nextBoolean(); Additionally JsonReader will now complain about non-literal unquoted name or value starts as being not a name / value instead of suggesting making the reader lenient when that would not help, e.g.: JsonReader reader = new JsonReader(new StringReader("=")); // Previously this threw exception suggesting to make reader lenient // However, lenient reader won't accept that JSON either reader.nextString();
…lues Previously a strict JsonReader suggested enabling lenient mode for multiple top level values even if the subsequent values would not be accepted in lenient mode either.
All callers which previously wanted isLiteral(...) to check whether the reader is lenient for comments are calling nextNonWhitespace(boolean) before that, which already performs the lenient check.
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
Based on #1743
Fixes #1564
Improves the location information shown in JsonReader exception messages and improves the tests by making them check the exception messages as well.
Improved location information:
Previously when the peeked token did not match the expected one, the exception message reported the location behind the token (instead of in front of it), e.g.:
Previously a strict reader would suggest lenient mode even in cases where lenient mode would not be able to read the JSON either.