1. 程式人生 > >如何用spring寫自己的處理器,如下劃線轉駝峰處理器

如何用spring寫自己的處理器,如下劃線轉駝峰處理器

前言

今天說下如何用Spring寫自己的一個引數處理器,相信大家在開發介面的時候都會遇到前端傳遞的引數是下劃線的,但是我們後端的規範確是用駝峰格式的,那麼這就需要一個引數綁定了,如果大家用過了這個jersey+ws(javax.ws.core)框架的開發restful介面,那麼這就不需要自己去實現這個功能了,但是你如果是spring boot/mvc的話就沒用這個功能了,spring暫時不支援引數繫結的,那麼久需要自己定義一個處理器了

如何處理?

一、jersey+ws框架

1、首先寫一個controller介面

    @POST
    @Path("/login")
    @Consumes(MediaType.APPLICATION_JSON)
    public Response login(@BeanParam UserForm form) {
        Map<String, String> map = server.login(form);
        return Tools.returnSuccess(map);
    }

2、建立UserForm接收引數

public class UserForm  {
	@QueryParam(“user_name”)
	private String userName;
	@QueryParam(“password”)
	private Date startTime;

ok,如果使用ws框架的話就使用@BeanParam和@QueryParam就可以實現引數綁定了,像@POST,@Path,@Consumes等都是ws裡的註解,這裡其他的一些註解為就不寫了,感興趣的可以請自己查閱資料

二、Spring MVC框架

這裡才是本章的重點,如果使用spring mvc作為restful介面來寫一個自己處理下劃線轉駝峰的處理器

ok,其實挺簡單的也只需要幾步就行了

1、建立controller

@RequestMapping(value = "/indexPage", method = RequestMethod.POST)
public String login(@LineConvertHump UserDto UserDto){
    
}

2、建立@UnderLineConvertHump

@Target(value = ElementType.PARAMETER)
@Retention(RetentionPolicy.RUNTIME)
public @interface LineConvertHump {
}

3、建立@LineConvertHump的處理器LineToHumpHandler

public class LineToHumpHandler implements HandlerMethodArgumentResolver{
    private static MappingJackson2HttpMessageConverter converter;

    static {
        converter = new MappingJackson2HttpMessageConverter();
    }

    @Override
    public boolean supportsParameter(MethodParameter parameter) {
        return parameter.hasParameterAnnotation(LineConvertHump.class);
    }

    private String underLineToCamel(String str) {
        Matcher matcher = Pattern.compile("_(\\w)").matcher(str);
        StringBuffer sb = new StringBuffer();
        while (matcher.find()) {
          matcher.appendReplacement(sb, matcher.group(1).toUpperCase());
        }
        matcher.appendTail(sb);
        return sb.toString();
    }

    @Override
    public Object resolveArgument (
            MethodParameter methodParameter,
            ModelAndViewContainer modelAndViewContainer,
            NativeWebRequest nativeWebRequest,
            WebDataBinderFactory webDataBinderFactory
    )
            throws Exception
    {

        HttpServletRequest servletRequest = nativeWebRequest.getNativeRequest(HttpServletRequest.class);
        ServletServerHttpRequest inputMessage = new ServletServerHttpRequest(servletRequest);
        Object result =null;
        try {
            Type genericParameterType = methodParameter.getGenericParameterType();
            String contentType = servletRequest.getContentType();
            if(MediaType.APPLICATION_JSON_VALUE.equals(contentType)){
                result = converter.read(Class.forName(genericParameterType.getTypeName()), inputMessage);
            }else{
                Object obj = BeanUtils.instantiate(methodParameter.getParameterType());
                BeanWrapper wrapper = PropertyAccessorFactory.forBeanPropertyAccess(obj);
                Map<String, String[]> parameterMap = nativeWebRequest.getParameterMap();
                for(Map.Entry<String, String[]> map : parameterMap.entrySet()){
                    String paramName = map.getKey();
                    String[] paramValue = map.getValue();
                    Field[] declaredFields = ReflectUtil.getAllFields(obj);
                    for (Field declaredField : declaredFields) {//如果pojo裡有帶下劃線則直接設定
                        if(declaredField.getName().contains("_")&¶mName.equals(declaredField.getName())){
                            wrapper.setPropertyValue(paramName, paramValue);
                            break;
                        }
                        String underLineParamName =underLineToCamel(paramName);
                        if(declaredField.getName().equals(underLineParamName)){
                            wrapper.setPropertyValue(underLineParamName, paramValue);
                            break;
                        }
                    }
                }
                result = obj;
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
        return result;
    }

}
4、交給spring管理引數處理器,這裡作用是專案啟動時候載入到spring中,在controller方法上加了@LineConvertHump就會走上面LineToHumpHandler處理器
@Configuration
public class MvcConfig extends WebMvcConfigurerAdapter {
    @Override
    public void addArgumentResolvers(List<HandlerMethodArgumentResolver> argumentResolvers) {
        argumentResolvers.add(new UnderlineToHumpHandler());
    }

    @Override
    public void configureMessageConverters(List<HttpMessageConverter<?>> converters) {
        converters.add(new FastJsonHttpMessageConverter());
        super.configureMessageConverters(converters);
    }

}
搞定了,覺得有用的點個贊,都是實戰中會用到的,持續更新中...