SpringBoot自定義逗號分隔轉集合註解
阿新 • • 發佈:2021-10-13
註解
package com.ccsa.common.core.annotation; import java.lang.annotation.ElementType; import java.lang.annotation.Retention; import java.lang.annotation.RetentionPolicy; import java.lang.annotation.Target; /** * @author hsn * 2021/10/13 * SpiltList */ @Target(ElementType.PARAMETER) @Retention(RetentionPolicy.RUNTIME) public @interface SpiltList { //分割符 String value() default ","; }
自定義解析器
package com.ccsa.common.data.resolver; import cn.hutool.core.util.StrUtil; import com.ccsa.common.core.annotation.SpiltList; import lombok.extern.slf4j.Slf4j; import org.springframework.core.MethodParameter; import org.springframework.web.bind.WebDataBinder; import org.springframework.web.bind.support.WebDataBinderFactory; import org.springframework.web.context.request.NativeWebRequest; import org.springframework.web.method.support.HandlerMethodArgumentResolver; import org.springframework.web.method.support.ModelAndViewContainer; import java.lang.reflect.Method; import java.lang.reflect.ParameterizedType; import java.lang.reflect.Type; import java.util.Arrays; import java.util.Objects; import java.util.stream.Collectors; /** * Get方法裡將逗號轉成list * 1,2,3 ----> [1,2,3] * @author hsn * 2021/10/13 * SplitListHandlerMethodArgumentResolver */ @Slf4j public class SplitListHandlerMethodArgumentResolver implements HandlerMethodArgumentResolver { /** * Whether the given {@linkplain MethodParameter method parameter} is * supported by this resolver. * 當引數裡有SpiltList註解則呼叫該解析器 * @param parameter the method parameter to check * @return {@code true} if this resolver supports the supplied parameter; * {@code false} otherwise */ @Override public boolean supportsParameter(MethodParameter parameter) { return parameter.hasParameterAnnotation(SpiltList.class); } /** * Resolves a method parameter into an argument value from a given request. * A {@link ModelAndViewContainer} provides access to the model for the * request. A {@link WebDataBinderFactory} provides a way to create * a {@link WebDataBinder} instance when needed for data binding and * type conversion purposes. * 解析過程 * @param parameter the method parameter to resolve. This parameter must * have previously been passed to {@link #supportsParameter} which must * have returned {@code true}. * @param mavContainer the ModelAndViewContainer for the current request * @param webRequest the current request * @param binderFactory a factory for creating {@link WebDataBinder} instances * @return the resolved argument value, or {@code null} if not resolvable * @throws Exception in case of errors with the preparation of argument values */ @Override public Object resolveArgument(MethodParameter parameter, ModelAndViewContainer mavContainer, NativeWebRequest webRequest, WebDataBinderFactory binderFactory) throws Exception { String requestParameter = webRequest.getParameter(Objects.requireNonNull(parameter.getParameterName())); SpiltList spiltList = parameter.getParameterAnnotation(SpiltList.class); assert requestParameter != null; assert spiltList != null; //獲取list裡的泛型 ParameterizedType parameterizedType = (ParameterizedType) parameter.getParameter().getParameterizedType(); if (parameterizedType.getActualTypeArguments().length == 0){ throw new RuntimeException("not found parameterizedType in List<>"); } Type actualTypeArgument = parameterizedType.getActualTypeArguments()[0]; if (!(actualTypeArgument instanceof Class)){ throw new RuntimeException("get class fail"); } if (StrUtil.isBlank(requestParameter)){ return Collections.emptyList(); } Class<?> type =(Class<?>) actualTypeArgument; String[] split = requestParameter.split(spiltList.value()); //呼叫泛型的valueOf方法,所以只支援基本的包裝型別,這裡也可以根據自己的需要進行處理 Method valueOfMethod = type.getMethod("valueOf", String.class); return Arrays.stream(split).map(item -> { try { return valueOfMethod.invoke(null, item); } catch (Exception e) { throw new RuntimeException(e); } }).collect(Collectors.toList()); } }
配置
package com.ccsa.common.data.mvc; import com.ccsa.common.data.resolver.SplitListHandlerMethodArgumentResolver; import org.springframework.context.annotation.Configuration; import org.springframework.web.method.support.HandlerMethodArgumentResolver; import org.springframework.web.servlet.config.annotation.WebMvcConfigurer; import java.util.List; /** * @author hsn * 2021/10/13 * WebConfig */ @Configuration public class WebConfig implements WebMvcConfigurer { @Override public void addArgumentResolvers(List<HandlerMethodArgumentResolver> resolvers) { resolvers.add(new SplitListHandlerMethodArgumentResolver()); } }
使用
@GetMapping("analyze")
public R analyze(@Size(min = 1,message = "專業id不能為空") @SpiltList List<Integer> majors) {
return R.ok(reviewService.analyse(majors));
}