31
31
import java .util .Comparator ;
32
32
import java .util .Set ;
33
33
34
+ import org .springframework .beans .BeanMetadataElement ;
34
35
import org .springframework .beans .factory .ObjectFactory ;
35
36
import org .springframework .beans .factory .config .TypedStringValue ;
36
37
import org .springframework .util .Assert ;
@@ -195,8 +196,8 @@ public static Class<?> resolveReturnTypeForFactoryMethod(Method method, Object[]
195
196
196
197
TypeVariable <Method >[] declaredTypeVariables = method .getTypeParameters ();
197
198
Type genericReturnType = method .getGenericReturnType ();
198
- Type [] methodArgumentTypes = method .getGenericParameterTypes ();
199
- Assert .isTrue (args .length == methodArgumentTypes .length , "Argument array does not match parameter count" );
199
+ Type [] methodParameterTypes = method .getGenericParameterTypes ();
200
+ Assert .isTrue (args .length == methodParameterTypes .length , "Argument array does not match parameter count" );
200
201
201
202
// Ensure that the type variable (e.g., T) is declared directly on the method
202
203
// itself (e.g., via <T>), not on the enclosing class or interface.
@@ -209,17 +210,33 @@ public static Class<?> resolveReturnTypeForFactoryMethod(Method method, Object[]
209
210
}
210
211
211
212
if (locallyDeclaredTypeVariableMatchesReturnType ) {
212
- for (int i = 0 ; i < methodArgumentTypes .length ; i ++) {
213
- Type currentMethodArgumentType = methodArgumentTypes [i ];
214
- if (currentMethodArgumentType .equals (genericReturnType )) {
215
- return args [i ].getClass ();
213
+ for (int i = 0 ; i < methodParameterTypes .length ; i ++) {
214
+ Type methodParameterType = methodParameterTypes [i ];
215
+ Object arg = args [i ];
216
+ if (methodParameterType .equals (genericReturnType )) {
217
+ if (arg instanceof TypedStringValue ) {
218
+ TypedStringValue typedValue = ((TypedStringValue ) arg );
219
+ if (typedValue .hasTargetType ()) {
220
+ return typedValue .getTargetType ();
221
+ }
222
+ try {
223
+ return typedValue .resolveTargetType (classLoader );
224
+ }
225
+ catch (ClassNotFoundException ex ) {
226
+ throw new IllegalStateException ("Failed to resolve typed value" , ex );
227
+ }
228
+ }
229
+ // Only consider argument type if it is a simple value...
230
+ if (arg != null && !(arg instanceof BeanMetadataElement )) {
231
+ return arg .getClass ();
232
+ }
233
+ return method .getReturnType ();
216
234
}
217
- if (currentMethodArgumentType instanceof ParameterizedType ) {
218
- ParameterizedType parameterizedType = (ParameterizedType ) currentMethodArgumentType ;
235
+ else if (methodParameterType instanceof ParameterizedType ) {
236
+ ParameterizedType parameterizedType = (ParameterizedType ) methodParameterType ;
219
237
Type [] actualTypeArguments = parameterizedType .getActualTypeArguments ();
220
238
for (Type typeArg : actualTypeArguments ) {
221
239
if (typeArg .equals (genericReturnType )) {
222
- Object arg = args [i ];
223
240
if (arg instanceof Class ) {
224
241
return (Class <?>) arg ;
225
242
}
@@ -229,7 +246,11 @@ public static Class<?> resolveReturnTypeForFactoryMethod(Method method, Object[]
229
246
className = (String ) arg ;
230
247
}
231
248
else if (arg instanceof TypedStringValue ) {
232
- className = ((TypedStringValue ) arg ).getValue ();
249
+ TypedStringValue typedValue = ((TypedStringValue ) arg );
250
+ String targetTypeName = typedValue .getTargetTypeName ();
251
+ if (targetTypeName == null || Class .class .getName ().equals (targetTypeName )) {
252
+ className = typedValue .getValue ();
253
+ }
233
254
}
234
255
if (className != null ) {
235
256
try {
@@ -240,11 +261,9 @@ else if (arg instanceof TypedStringValue) {
240
261
"Could not resolve specified class name argument [" + arg + "]" , ex );
241
262
}
242
263
}
243
- else {
244
- // Consider adding logic to determine the class of the typeArg, if possible.
245
- // For now, just fall back...
246
- return method .getReturnType ();
247
- }
264
+ // Consider adding logic to determine the class of the typeArg, if possible.
265
+ // For now, just fall back...
266
+ return method .getReturnType ();
248
267
}
249
268
}
250
269
}
0 commit comments