In Spring Boot project, the configuration in the YML file can be automatically converted to an @ConfigurationProperties annotated bean, I found from the official documents and source code in ApplicationConversionService#addApplicationConverters() method to add A default LenientStringToEnumConverterFactory to handle all the String conversion to Enum, it through the Enum.valueOf() implementation,But I want to use other rules to turn strings into examples of enum,Just like the fromAlias() method below,
@ConfigurationProperties(prefix = "head")
@Component
@Data
public class HeadProperties {
private PayType payType;
private Integer cast;
@Getter
@RequiredArgsConstructor
enum PayType {
GOLD("GOLD", "金币"), DIAMOND("DIAMOND", "钻石"), VIP_FREE("VIP_FREE", "会员免费");
private final String val;
private final String alias;
static PayType fromAlias(String alias) {
return Arrays.stream(values())
.filter(type -> alias.equals(type.getAlias()))
.findAny()
.orElse(null);
}
}
}
The following is the YML file configuration
head:
payType: "金币"
cast: 10
I don't know where the entry is, so I get an error as soon as the program runs code:
@SpringBootApplication
@Slf4j
public class DemoApplication{
public static void main(String[] args) {
SpringApplication.run(DemoApplication.class, args);
}
@Bean
ApplicationRunner runner(HeadProperties headConfig) {
return arg -> log.info("head config:{}", headConfig);
}
}
the following is error message:
APPLICATION FAILED TO START
***************************
Description:
Failed to bind properties under 'head.pay-type' to com.example.demo.HeadProperties$PayType:
Property: head.pay-type
Value: 金币
Origin: class path resource [application.yml] - 2:12
Reason: failed to convert java.lang.String to com.example.demo.HeadProperties$PayType (caused by java.lang.IllegalArgumentException: No enum constant com.example.demo.HeadProperties.PayType.金币)
Action:
Update your application's configuration. The following values are valid:
DIAMOND
GOLD
VIP_FREE
I tried injecting various converters like the one below into the container,but it still didn't work.
@Component
public class PayTypeConverter implements Converter<String, HeadProperties.PayType> {
@Override
public HeadProperties.PayType convert(String source) {
return HeadProperties.PayType.fromAlias(source);
}
}
@Component
public class PayTypeConverter implements Converter<String, Enum<HeadProperties.PayType>> {
@Override
public Enum<HeadProperties.PayType> convert(String source) {
return HeadProperties.PayType.fromAlias(source);
}
}
How can this requirement be fulfilled?