Skip to content

Commit 801c8ed

Browse files
committed
Revise type resolution for alignment with AbstractJsonHttpMessageConverter
See gh-21188
1 parent cd6085a commit 801c8ed

File tree

1 file changed

+35
-24
lines changed

1 file changed

+35
-24
lines changed

Diff for: spring-web/src/main/java/org/springframework/http/converter/json/KotlinSerializationJsonHttpMessageConverter.java

+35-24
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,7 @@
2727
import kotlinx.serialization.SerializersKt;
2828
import kotlinx.serialization.json.Json;
2929

30+
import org.springframework.core.GenericTypeResolver;
3031
import org.springframework.http.HttpInputMessage;
3132
import org.springframework.http.HttpOutputMessage;
3233
import org.springframework.http.MediaType;
@@ -46,6 +47,7 @@
4647
*
4748
* @author Andreas Ahlenstorf
4849
* @author Sebastien Deleuze
50+
* @author Juergen Hoeller
4951
* @since 5.3
5052
*/
5153
public class KotlinSerializationJsonHttpMessageConverter extends AbstractGenericHttpMessageConverter<Object> {
@@ -56,6 +58,7 @@ public class KotlinSerializationJsonHttpMessageConverter extends AbstractGeneric
5658

5759
private final Json json;
5860

61+
5962
/**
6063
* Construct a new {@code KotlinSerializationJsonHttpMessageConverter} with the default configuration.
6164
*/
@@ -71,10 +74,11 @@ public KotlinSerializationJsonHttpMessageConverter(Json json) {
7174
this.json = json;
7275
}
7376

77+
7478
@Override
7579
protected boolean supports(Class<?> clazz) {
7680
try {
77-
resolve(clazz);
81+
serializer(clazz);
7882
return true;
7983
}
8084
catch (Exception ex) {
@@ -83,37 +87,45 @@ protected boolean supports(Class<?> clazz) {
8387
}
8488

8589
@Override
86-
protected Object readInternal(Class<?> clazz, HttpInputMessage inputMessage) throws IOException, HttpMessageNotReadableException {
87-
return this.read(clazz, null, inputMessage);
90+
public final Object read(Type type, @Nullable Class<?> contextClass, HttpInputMessage inputMessage)
91+
throws IOException, HttpMessageNotReadableException {
92+
93+
return decode(serializer(GenericTypeResolver.resolveType(type, contextClass)), inputMessage);
8894
}
8995

9096
@Override
91-
public Object read(Type type, @Nullable Class<?> contextClass, HttpInputMessage inputMessage) throws IOException, HttpMessageNotReadableException {
97+
protected final Object readInternal(Class<?> clazz, HttpInputMessage inputMessage)
98+
throws IOException, HttpMessageNotReadableException {
99+
100+
return decode(serializer(clazz), inputMessage);
101+
}
102+
103+
private Object decode(KSerializer<Object> serializer, HttpInputMessage inputMessage)
104+
throws IOException, HttpMessageNotReadableException {
105+
92106
MediaType contentType = inputMessage.getHeaders().getContentType();
93107
String jsonText = StreamUtils.copyToString(inputMessage.getBody(), getCharsetToUse(contentType));
94108
try {
95109
// TODO Use stream based API when available
96-
return this.json.decodeFromString(resolve(type), jsonText);
110+
return this.json.decodeFromString(serializer, jsonText);
97111
}
98112
catch (SerializationException ex) {
99113
throw new HttpMessageNotReadableException("Could not read JSON: " + ex.getMessage(), ex, inputMessage);
100114
}
101115
}
102116

103117
@Override
104-
protected void writeInternal(Object o, HttpOutputMessage outputMessage) throws HttpMessageNotWritableException {
105-
try {
106-
this.writeInternal(o, o.getClass(), outputMessage);
107-
}
108-
catch (IOException ex) {
109-
throw new HttpMessageNotWritableException("Could not write JSON: " + ex.getMessage(), ex);
110-
}
118+
protected final void writeInternal(Object object, @Nullable Type type, HttpOutputMessage outputMessage)
119+
throws IOException, HttpMessageNotWritableException {
120+
121+
encode(object, serializer(type != null ? type : object.getClass()), outputMessage);
111122
}
112123

113-
@Override
114-
protected void writeInternal(Object o, @Nullable Type type, HttpOutputMessage outputMessage) throws IOException, HttpMessageNotWritableException {
124+
private void encode(Object object, KSerializer<Object> serializer, HttpOutputMessage outputMessage)
125+
throws IOException, HttpMessageNotWritableException {
126+
115127
try {
116-
String json = this.json.encodeToString(resolve(type), o);
128+
String json = this.json.encodeToString(serializer, object);
117129
MediaType contentType = outputMessage.getHeaders().getContentType();
118130
outputMessage.getBody().write(json.getBytes(getCharsetToUse(contentType)));
119131
outputMessage.getBody().flush();
@@ -134,21 +146,20 @@ private Charset getCharsetToUse(@Nullable MediaType contentType) {
134146
}
135147

136148
/**
137-
* Tries to find a serializer that can marshall or unmarshall instances of the given type using
138-
* kotlinx.serialization. If no serializer can be found, an exception is thrown.
139-
* <p>
140-
* Resolved serializers are cached and cached results are returned on successive calls.
141-
*
142-
* @param type to find a serializer for.
143-
* @return resolved serializer for the given type.
144-
* @throws RuntimeException if no serializer supporting the given type can be found.
149+
* Tries to find a serializer that can marshall or unmarshall instances of the given type
150+
* using kotlinx.serialization. If no serializer can be found, an exception is thrown.
151+
* <p>Resolved serializers are cached and cached results are returned on successive calls.
152+
* @param type the type to find a serializer for
153+
* @return a resolved serializer for the given type
154+
* @throws RuntimeException if no serializer supporting the given type can be found
145155
*/
146-
private KSerializer<Object> resolve(Type type) {
156+
private KSerializer<Object> serializer(Type type) {
147157
KSerializer<Object> serializer = serializerCache.get(type);
148158
if (serializer == null) {
149159
serializer = SerializersKt.serializer(type);
150160
serializerCache.put(type, serializer);
151161
}
152162
return serializer;
153163
}
164+
154165
}

0 commit comments

Comments
 (0)