情况 前端 String 后端 enum
前端
后端
报错
2024-05-31T21:47:40.618+08:00 WARN 21360 --- [nio-8080-exec-6] .w.s.m.s.DefaultHandlerExceptionResolver :
Resolved [org.springframework.web.method.annotation.MethodArgumentTypeMismatchException:
Failed to convert value of type 'java.lang.String' to required type 'com.orchids.springmybatisplus.model.enums.Sex';
Failed to convert from type
[java.lang.String] to type [@org.springframework.web.bind.annotation.RequestParam
com.orchids.springmybatisplus.model.enums.Sex] for value '1']
问题出现在这个方法
//根据性别查询学生 存在String --->转换为enums\
@Operation(summary = "根据性别(类型)查询学生信息")
@GetMapping("sex") //@RequestParam(required = false) required=false 表示参数可以没有
public Result<List<Student>> StudentBySex(@RequestParam(required = false) Sex sex){
LambdaQueryWrapper<Student> lambdaQueryWrapper = new LambdaQueryWrapper<>();
lambdaQueryWrapper.eq(Student::getSex,sex);
List<Student> list = studentService.list(lambdaQueryWrapper);
return Result.ok(list);
}
对应的枚举类
package com.orchids.springmybatisplus.model.enums;
import com.baomidou.mybatisplus.annotation.EnumValue;
import com.fasterxml.jackson.annotation.JsonValue;
/**
* @Author qwh
* @Date 2024/5/31 19:13
*/
public enum Sex implements BaseEnum{
MAN(0,"男性"),
WOMAN(1, "女性");
@EnumValue
@JsonValue
private Integer code;
private String name;
Sex(Integer code, String name) {
this.code = code;
this.name = name;
}
@Override
public Integer getCode() {
return this.code;
}
@Override
public String getName() {
return this.name;
}
}
解决方法 一
- 编写StringToSexConverter方法
package com.orchids.lovehouse.web.admin.custom.converter;
import com.orchids.lovehouse.model.enums.ItemType;
import org.springframework.core.convert.converter.Converter;
import org.springframework.stereotype.Component;
@Component
public class StringToItemTypeConverter implements Converter<String, ItemType> {
/**
* 根据给定的代码字符串转换为对应的ItemType枚举。
*
* @param code 代表ItemType枚举的代码字符串,该代码应该是整数形式。
* @return 对应于给定代码的ItemType枚举值。
* @throws IllegalArgumentException 如果给定的代码无法匹配到任何枚举值时抛出。
*/
@Override
public ItemType convert(String code) {
// 遍历所有ItemType枚举值,查找与给定代码匹配的枚举
for (ItemType value : ItemType.values()) {
if (value.getCode().equals(Integer.valueOf(code))) {
return value;
}
}
// 如果没有找到匹配的枚举,抛出异常
throw new IllegalArgumentException("code非法");
}
}
将其注册到WebMvcConfiguration
package com.orchids.springmybatisplus.web.custom.config;
import com.orchids.springmybatisplus.web.custom.converter.StringToSexConverter;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Configuration;
import org.springframework.format.FormatterRegistry;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;
/**
* @Author qwh
* @Date 2024/5/31 22:06
*/
@Configuration
public class WebMvcConfiguration implements WebMvcConfigurer {
@Autowired
private StringToSexConverter stringToItemTypeConverter;
@Override
public void addFormatters(FormatterRegistry registry) {
registry.addConverter(this.stringToItemTypeConverter);
}
}
成功解决
- 当有很多种类型需要转换 例如`
- String
到
Integer`、 String
到Date
,String
到Boolean
- 就要写每一种转换方法 代码重用性不高
- 于是就有了第二种方法
- 使用
[ConverterFactory](https://docs.spring.io/spring-framework/reference/core/validation/convert.html#core-convert-ConverterFactory-SPI)
接口更为合适,这个接口可以将同一个转换逻辑应用到一个接口的所有实现类,因此我们可以定义一个BaseEnum
接口,然后另所有的枚举类都实现该接口,然后就可以自定义ConverterFactory
,集中编写各枚举类的转换逻辑了 - 具体实现如下
- 在编写一个BaseEnum接口
- String
public interface BaseEnum {
Integer getCode();
String getName();
}
- 让enums 包下的枚举都实现这个接口
package com.orchids.springmybatisplus.model.enums;
import com.baomidou.mybatisplus.annotation.EnumValue;
import com.fasterxml.jackson.annotation.JsonValue;
/**
* @Author qwh
* @Date 2024/5/31 19:13
*/
public enum Sex implements BaseEnum{
MAN(0,"男性"),
WOMAN(1, "女性");
@EnumValue
@JsonValue
private Integer code;
private String name;
Sex(Integer code, String name) {
this.code = code;
this.name = name;
}
@Override
public Integer getCode() {
return this.code;
}
@Override
public String getName() {
return this.name;
}
}
- 编写 StringToBaseEnumConverterFactory 实现接口 ConverterFactory
@Component
public class StringToBaseEnumConverterFactory implements ConverterFactory<String, BaseEnum> {
@Override
public <T extends BaseEnum> Converter<String, T> getConverter(Class<T> targetType) {
return new Converter<String, T>() {
@Override
public T convert(String source) {
for (T enumConstant : targetType.getEnumConstants()) {
if (enumConstant.getCode().equals(Integer.valueOf(source))) {
return enumConstant;
}
}
throw new IllegalArgumentException("非法的枚举值:" + source);
}
};
}
}
- 将其注册到WebMvcConfiguration
package com.orchids.springmybatisplus.web.custom.config;
import com.orchids.springmybatisplus.web.custom.converter.StringToBaseEnumConverterFactory;
import com.orchids.springmybatisplus.web.custom.converter.StringToSexConverter;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Configuration;
import org.springframework.format.FormatterRegistry;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;
/**
* @Author qwh
* @Date 2024/5/31 22:06
*/
@Configuration
public class WebMvcConfiguration implements WebMvcConfigurer {
@Autowired
private StringToBaseEnumConverterFactory stringToBaseEnumConverterFactory;
@Override
public void addFormatters(FormatterRegistry registry) {
registry.addConverterFactory(this.stringToBaseEnumConverterFactory);
}
}
第二种方法有这一个类就行了