Skip to content

Commit 032b52e

Browse files
committed
android-record: Adapt generic types returned by Android reflection to follow Java behavior.
1 parent 862ff03 commit 032b52e

File tree

1 file changed

+28
-5
lines changed

1 file changed

+28
-5
lines changed

android-record/src/main/java/com/fasterxml/jackson/module/androidrecord/AndroidRecordModule.java

+28-5
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,6 @@
11
package com.fasterxml.jackson.module.androidrecord;
22

3-
import java.lang.reflect.Field;
4-
import java.lang.reflect.Modifier;
5-
import java.lang.reflect.Parameter;
6-
import java.lang.reflect.Type;
3+
import java.lang.reflect.*;
74
import java.util.*;
85
import java.util.stream.Collectors;
96
import java.util.stream.Stream;
@@ -119,7 +116,7 @@ public PotentialCreator findDefaultCreator(MapperConfig<?> config,
119116
AnnotatedConstructor constructor = (AnnotatedConstructor) creator.creator();
120117
Parameter[] parameters = constructor.getAnnotated().getParameters();
121118
Map<String, Type> parameterTypes = Arrays.stream(parameters)
122-
.collect(Collectors.toMap(Parameter::getName, Parameter::getParameterizedType));
119+
.collect(Collectors.toMap(Parameter::getName, parameter -> fixAndroidGenericType(parameter.getParameterizedType())));
123120

124121
if (parameterTypes.equals(components)) {
125122
if (foundCreator != null) {
@@ -150,4 +147,30 @@ static boolean isDesugaredRecordClass(Class<?> raw) {
150147
static Stream<Field> getDesugaredRecordComponents(Class<?> raw) {
151148
return Arrays.stream(raw.getDeclaredFields()).filter(field -> !Modifier.isStatic(field.getModifiers()));
152149
}
150+
151+
static Class<?> arrayTypeCompat(Class<?> componentType) {
152+
return Array.newInstance(componentType, 0).getClass();
153+
}
154+
155+
static Type fixAndroidGenericType(Type type) {
156+
if (type instanceof GenericArrayType) {
157+
//recurse into component type
158+
Type componentType = fixAndroidGenericType(((GenericArrayType) type).getGenericComponentType());
159+
if (componentType instanceof Class<?>) { //if it isn't generic, return the raw array type
160+
return arrayTypeCompat((Class<?>) componentType);
161+
}
162+
}
163+
else if (type instanceof ParameterizedType) {
164+
//if the parameterized type is not actually parameterized, deduce the raw type
165+
ParameterizedType parameterizedType = (ParameterizedType) type;
166+
Type rawType = parameterizedType.getRawType();
167+
if (rawType instanceof Class<?>) {
168+
Class<?> rawComponentClass = (Class<?>) rawType;
169+
if (rawComponentClass.getTypeParameters().length == 0) {
170+
return rawComponentClass;
171+
}
172+
}
173+
}
174+
return type;
175+
}
153176
}

0 commit comments

Comments
 (0)