spring-projects / spring-projects/spring-framework
`GenericConversionService` selects incorrect converter for `String` to `List<String>` conversion
Open
@sdeleuze is already working on this.
Since Jun 17, 2025.
in: core
status: waiting-for-internal-feedback
status: waiting-for-triage
- Dominant language
- Java
- Stars
- 60.2k
- Forks
- 38.8k
- Avg merge
- 5d 2h
- Merged PRs (30d)
- 27
Description
This issue is related to #34535 and #34298.
Converter<String, List<? extends Map<String, ?>>> is incorrectly selected when converting a String to a List<String>.
The following reproducer test fails on all 6.2.x versions except 6.2.3:
package com.example;
import org.junit.jupiter.api.Test;
import org.springframework.core.convert.TypeDescriptor;
import org.springframework.core.convert.converter.Converter;
import org.springframework.core.convert.support.GenericConversionService;
import org.springframework.core.convert.support.StringToCollectionConverter;
import java.util.List;
import java.util.Map;
import static org.assertj.core.api.Assertions.assertThat;
class GenericConversionServiceTests {
private final GenericConversionService conversionService = new GenericConversionService();
@Test
@SuppressWarnings("unchecked")
void stringToListOfString() {
conversionService.addConverter(new StringToCollectionConverter(conversionService));
conversionService.addConverter(new StringToListOfMapConverter());
List<String> result = (List<String>) conversionService.convert("foo,bar",
TypeDescriptor.valueOf(String.class),
TypeDescriptor.collection(List.class, TypeDescriptor.valueOf(String.class))
);
assertThat(result.get(0)).isEqualTo("foo");
}
private static class StringToListOfMapConverter implements Converter<String, List<? extends Map<String, ?>>> {
@Override
public List<? extends Map<String, ?>> convert(String source) {
return List.of(Map.of("bar", source));
}
}
// Using this version of the converter also results in a failure
private static class StringToListOfMapConverterWithoutWildcard implements Converter<String, List<Map<String, ?>>> {
@Override
public List<Map<String, ?>> convert(String source) {
return List.of(Map.of("bar", source));
}
}
}
The exception shows that the StringToListOfMapConverter converter was chosen instead of expected StringToCollectionConverter:
class java.util.ImmutableCollections$Map1 cannot be cast to class java.lang.String (java.util.ImmutableCollections$Map1 and java.lang.String are in module java.base of loader 'bootstrap')
java.lang.ClassCastException: class java.util.ImmutableCollections$Map1 cannot be cast to class java.lang.String (java.util.ImmutableCollections$Map1 and java.lang.String are in module java.base of loader 'bootstrap')
at org.springframework.core.convert.support.GenericConversionServiceTests.stringToListOfString(GenericConversionServiceTests.java:28)
at java.base/java.lang.reflect.Method.invoke(Method.java:565)
at java.base/java.util.ArrayList.forEach(ArrayList.java:1604)
at java.base/java.util.ArrayList.forEach(ArrayList.java:1604)
Contributor guide
First steps
- Read the whole issue, then the project's contributing guide.
- Comment on the issue to say you are picking it up — it saves two people doing the same work.
- Fork the repository and make your change on a branch.
- Open a pull request that references the issue number.
Assessment
This issue has not been assessed yet.