google / google/gson

Registering an `ExclusionStrategy` for deserialization affects serialized output

Open
#2,190 0 comments 0 reactions 0 assignees View on GitHub
bug
Dominant language
Java
Stars
24.2k
Forks
4.5k
Avg merge
6d 4h
Merged PRs (30d)
12

Description

# Gson version
2.9.1

# Java / Android version
Java 17

# Description
Registering an `ExclusionStrategy` which excludes a subclass on *de*serialization affects the serialized output for that class.
The underlying issue is the same as for #1833 and #2032.

Maybe at this point there should be a method `TypeAdapter.usesReflection()` whose default implementation returns `false` but which can be overridden by subclasses. This would avoid all this special-casing, and it would also allow third-party adapters to make use of this.

Important: Fixing this might affect the exclusion handling for serialization, so maybe this cannot be solved easily.

# Reproduction steps
```java
static class Base {
}
static class Sub extends Base {
int i = 0;
}
static class Container {
Base b = new Sub();
}

@Test
public void test() {
ExclusionStrategy exclusionStrategy = new ExclusionStrategy() {
@Override public boolean shouldSkipField(FieldAttributes f) {
return false;
}

@Override public boolean shouldSkipClass(Class clazz) {
return clazz == Sub.class;
}
};

Gson gson = new GsonBuilder()
.registerTypeAdapter(Base.class, new TypeAdapter() {
@Override public Base read(JsonReader in) throws IOException {
throw new AssertionError("not needed");
}

@Override public void write(JsonWriter out, Base value) throws IOException {
out.value("custom-adapter");
}
})
// Registering a *de*serialization exclusion affects serialization
.addDeserializationExclusionStrategy(exclusionStrategy)
.create();

assertEquals("{\"b\":\"custom-adapter\"}", gson.toJson(new Container()));
}
```
When the `ExclusionStrategy` is registered, `TypeAdapterRuntimeTypeWrapper` erroneously considers the adapter created by `Excluder` (which wraps a reflective adapter) as non-reflective. The assertion above fails because the output is erroneously `{"b":{"i":0}}`.

Contributor guide

Open the contributing guide

Assessment

This issue has not been assessed yet.

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.