【问题标题】:How allow case-insensitive mapping of enums in jackson/Spring boot?如何在杰克逊/春季启动中允许不区分大小写的枚举映射?
【发布时间】:2018-08-16 22:45:14
【问题描述】:

注意:这不是重复的。另一个问题与 Spring 请求参数的自动编组无关。它有一个解决方案,您可以使用 jackson 手动编组对象。

我希望允许开发人员使用可以不区分大小写的枚举来创建请求对象。其他字段/属性可能需要区分大小写匹配,但枚举应该不区分大小写。

到目前为止,我发现的唯一方法 (initBinding) 要求您在编译时指定确切的枚举类。我正在寻找一种更通用的方法来将 JSON 请求中的字符串编组为枚举。

目前我发现的唯一方法:

@RestController
public class TestController
{
    //...elided...

    @InitBinder
    public void initBinder(final WebDataBinder webdataBinder)
    {
        webdataBinder.registerCustomEditor( MyEnum.class, new CaseInsensitiveEnumConverter() );
    }
}

但这需要使用已知的枚举进行编译。

【问题讨论】:

    标签: java spring spring-boot enums jackson


    【解决方案1】:

    从 spring 2.0 开始,在 application.properties 中设置以下内容就足够了:

    spring.jackson.mapper.accept-case-insensitive-enums = true 
    

    【讨论】:

    • 试图将它与 webclient.get() 一起使用.... - 不适用于最新的 Spring...
    【解决方案2】:

    你可以看到org.springframework.core.convert.support.StringToEnumConverterFactory这个类,所以你可以像这样自定义你自己的converterFactory。

    public class MyStringToEnumConverterFactory implements ConverterFactory<String, Enum> {
    
    @Override
    public <T extends Enum> Converter<String, T> getConverter(Class<T> targetType) {
        return new StringToEnum(getEnumType(targetType));
    }
    
    private class StringToEnum<T extends Enum> implements Converter<String, T> {
    
        private final Class<T> enumType;
    
        public StringToEnum(Class<T> enumType) {
            this.enumType = enumType;
        }
    
        @Override
        public T convert(String source) {
            if (source.isEmpty()) {
                // It's an empty enum identifier: reset the enum value to null.
                return null;
            }
    
            return (T) Enum.valueOf(this.enumType, source.trim().toUpperCase());
        }
    }
    
    private static Class<?> getEnumType(Class targetType) {
        Class<?> enumType = targetType;
        while (enumType != null && !enumType.isEnum()) {
            enumType = enumType.getSuperclass();
        }
        if (enumType == null) {
            throw new IllegalArgumentException(
                    "The target type " + targetType.getName() + " does not refer to an enum");
        }
        return enumType;
    }
    }
    

    并添加到 ConverterRegistry 。

    @Configuration
    public class MyConfiguration {
    
    @Bean
    public ConverterRegistry initConverter(ConverterRegistry registry) {
        registry.addConverterFactory(new MyStringToEnumConverterFactory());
        return registry;
    }
    }
    

    希望能帮到你!

    【讨论】:

      猜你喜欢
      • 2011-10-22
      • 2014-08-01
      • 2015-12-23
      • 1970-01-01
      • 2021-02-07
      • 2016-04-15
      • 1970-01-01
      • 2015-10-19
      • 2016-01-20
      相关资源
      最近更新 更多