温馨提示×

温馨提示×

您好,登录后才能下订单哦!

密码登录×
登录注册×
其他方式登录
点击 登录注册 即表示同意《亿速云用户服务条款》

如何在spring boot项目中使用枚举

发布时间:2021-03-23 17:02:45 来源:亿速云 阅读:863 作者:Leah 栏目:编程语言

如何在spring boot项目中使用枚举?很多新手对此不是很清楚,为了帮助大家解决这个难题,下面小编将为大家详细讲解,有这方面需求的人可以来学习下,希望你能有所收获。

1. 在controller的方法中,比如以这个枚举为参数,如下代码:

@RequestMapping("/**")
  public String getRejectReasons(EnumExpenseType type) {
    return "";
  }

前台传入的参数如果是type:1, 那它值应该是:小欢喜,实际上呢?

Caused by: java.lang.IllegalArgumentException: No enum constant com.**.EnumReasonType.1	at java.lang.Enum.valueOf(Enum.java:238) ~[?:1.8.0_111]	at org.springframework.core.convert.support.StringToEnumConverterFactory$StringToEnum.convert(StringToEnumConverterFactory.java:52) ~[spring-core-5.1.8.RELEASE.jar:5.1.8.RELEASE]	at org.springframework.core.convert.support.StringToEnumConverterFactory$StringToEnum.convert(StringToEnumConverterFactory.java:38) ~[spring-core-5.1.8.RELEASE.jar:5.1.8.RELEASE]	at org.springframework.core.convert.support.GenericConversionService$ConverterFactoryAdapter.convert(GenericConversionService.java:436) ~[spring-core-5.1.8.RELEASE.jar:5.1.8.RELEASE]	at org.springframework.core.convert.support.ConversionUtils.invokeConverter(ConversionUtils.java:41) ~[spring-core-5.1.8.RELEASE.jar:5.1.8.RELEASE]	at org.springframework.core.convert.support.GenericConversionService.convert(GenericConversionService.java:191) ~[spring-core-5.1.8.RELEASE.jar:5.1.8.RELEASE]	at org.springframework.beans.TypeConverterDelegate.convertIfNecessary(TypeConverterDelegate.java:129) ~[spring-beans-5.1.7.RELEASE.jar:5.1.7.RELEASE]	at org.springframework.beans.TypeConverterSupport.convertIfNecessary(TypeConverterSupport.java:73) ~[spring-beans-5.1.7.RELEASE.jar:5.1.7.RELEASE]	at org.springframework.beans.TypeConverterSupport.convertIfNecessary(TypeConverterSupport.java:53) ~[spring-beans-5.1.7.RELEASE.jar:5.1.7.RELEASE]	at org.springframework.validation.DataBinder.convertIfNecessary(DataBinder.java:693) ~[spring-context-5.1.7.RELEASE.jar:5.1.7.RELEASE]	at org.springframework.web.method.annotation.AbstractNamedValueMethodArgumentResolver.resolveArgument(AbstractNamedValueMethodArgumentResolver.java:124) ~[spring-web-5.1.7.RELEASE.jar:5.1.7.RELEASE]	... 81 more

Failed to convert value of type 'java.lang.String' to required type 'com.**.EnumExpenseType';
nested exception is org.springframework.core.convert.ConversionFailedException:
Failed to convert from type [java.lang.String] to type [com.**.EnumExpenseType] for value '1';
nested exception is java.lang.IllegalArgumentException: No enum constant com.***.EnumExpenseType.1

实际上它却报了个错。转换失败了。

查看报错信息,可以定位到是spring框架中StringToEnumConverterFactory中转换失败,具体代码如下:

private static 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()); 
    }
  }

是Enum.valueOf这里报错,Enum.valueOf的后面的值并不是我们的value,而是name(这里的小欢喜)。

所以,我们不能使用这个spring提供converter,需要自定义一个:StringToEnumConverterFactory

public class StringToEnumConverterFactory implements ConverterFactory<String, BaseEnum> {

  private static final Map<Class, Converter> converterMap = new HashMap<>();

  @Override
  public <T extends BaseEnum> Converter<String, T> getConverter(Class<T> targetType) {
    Converter<String, T> converter = converterMap.get(targetType);
    if(converter == null) {
      converter = new StringToEnumConverter<>(targetType);
      converterMap.put(targetType, converter);
    }
    return converter;
  }

  class StringToEnumConverter<T extends BaseEnum> implements Converter<String, T> {
    private Map<String, T> enumMap = new HashMap<>();

    StringToEnumConverter(Class<T> enumType) {
      T[] enums = enumType.getEnumConstants();
      for(T e : enums) {
        enumMap.put(String.valueOf(e.getValue()), e);
      }
    }

    @Override
    public T convert(String source) {

      T t = enumMap.get(source);
      if (t == null) {
        // 异常可以稍后去捕获
        throw new IllegalArgumentException("No element matches " + source);
      }
      return t;
    }
  }

}

然后再将这个工厂配置到项目中WebMvcConfigurationSupport:

@Override
  public void addFormatters(FormatterRegistry registry) {
    registry.addConverterFactory(new StringToEnumConverterFactory());

  }

看完上述内容是否对您有帮助呢?如果还想对相关知识有进一步的了解或阅读更多相关文章,请关注亿速云行业资讯频道,感谢您对亿速云的支持。

向AI问一下细节

免责声明:本站发布的内容(图片、视频和文字)以原创、转载和分享为主,文章观点不代表本网站立场,如果涉及侵权请联系站长邮箱:is@yisu.com进行举报,并提供相关证据,一经查实,将立刻删除涉嫌侵权内容。

AI