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.
Why this is useful: Suppose you have a class with a lot of fields. Most of them can be easily interpreted by the Gson reader, possibly with a field naming strategy. But some have such weird names that the field naming strategy might not necessarily properly match them to the target properties. Especially if the JSON comes from a third party (like an API), the best course of action as of today is to create your own
TypeAdapter
and manually map all of the fields, including the ones that GSON could map on it's own. This is why I added the "Fill-In" feature. TheregisterTypeAdapterWithFillIn
method allows you to manually define only the fields that Gson can not map properly, while not having to map trivial mappings.Implementation Details: The way to register a custom adapter with Fill-in is through the
GsonBuilder#registerTypeAdapterWithFillIn
method. This method wraps the adapter into a constructor object that is then passed to an instance of theReflectiveTypeAdapterFactory.Adapter
class. In other words, when theread
method is called on aReflectiveTypeAdapterFactory.Adapter
instance, theObjectContstructor
object calls the custom adapter and generates an instance of the target class whose fields are written to or overwritten (see the Conditions section).When calling the
create
method on theReflectiveTypeAdapterFactory
responsible for producing a fill-in adapter, it will only return the adapter when the target type is or is a subclass of the desired target class. This is unlike the usualReflectiveTypeAdapterFactory
instances which serve to create a catch-all type adapter for non-standard classes.In order to support the construction of instances while reading from the input
JsonReader
, theInstanceCreator
andObjectConstructor
have methods that accept aJsonReader
object. If not overridden by the implementation, they default to the normalconstruct
method (for backwards compatibility).I wrote some tests in the
test/.../gson/internal/bind/LayeredAdapterTest.java
class to demonstrate and test some common use cases that I thought of for this feature.Notes:
@Expose
annotation to the fields that you want to be protected from overwriting.default
methods in interfaces, this only supports java versions of 8+, and will fail the travis-ci check. I would really appreciate if someone pointed out a way to achieve the same thing in a backwards-compatible way without relying on Java 8 features. Also, if there is going to be a multi-release jar as suggested in java.lang.NumberFormatException: For input string: "11-ea" #1469, this can go in the java 8+ jar.