springmvc @RequestBody String类型参数

通过如下配置:

   <bean id="mappingJacksonHttpMessageConverter"
          class="org.springframework.http.converter.json.MappingJackson2HttpMessageConverter">
        <property name="supportedMediaTypes">
            <list>
                <value>text/html;charset=UTF-8</value>
                <value>application/json;charset=UTF-8</value>
            </list>
        </property>
    </bean>
    <!-- 启动SpringMVC的注解功能,完成请求和注解POJO的映射 -->
    <bean class="org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerMapping"/>
    <bean class="org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter">
        <property name="messageConverters">
            <list>
                <ref bean="mappingJacksonHttpMessageConverter"/>
                <!-- JSON转换器 -->
            </list>
        </property>
    </bean> 
  •  

spring mvc的Controller层使用@RequestBody接收Content-Type为application/json的数据时,默认支持Map方式和对象方式参数

@RequestMapping(value = "/{code}/saveUser", method = RequestMethod.POST)
    @ResponseBody
    public JsonResult saveUser(@PathVariable("code") Integer code, @RequestBody Map<String, Object> datas,@RequestBody User user) {
    。。。
    }

如果是一个参数时也需要用个Map或者对象处理,使用String会报解析错误,具体看:AbstractJackson2HttpMessageConverter的方法read(Type type, Class

@Override
    public Object read(Type type, Class<?> contextClass, HttpInputMessage inputMessage)
            throws IOException, HttpMessageNotReadableException {

        JavaType javaType = getJavaType(type, contextClass);
        return readJavaType(javaType, inputMessage);
    }

    private Object readJavaType(JavaType javaType, HttpInputMessage inputMessage) {
        try {
            return this.objectMapper.readValue(inputMessage.getBody(), javaType);
        }
        catch (IOException ex) {
            throw new HttpMessageNotReadableException("Could not read JSON: " + ex.getMessage(), ex);
        }
    }

为了让@RequestBody支持String参数(目前只支持接收单个参数) 
重写org.springframework.http.converter.json.MappingJackson2HttpMessageConverter类

package com.test.converter.json
import org.springframework.http.HttpInputMessage;
import org.springframework.http.converter.HttpMessageNotReadableException;
import org.springframework.http.converter.json.MappingJackson2HttpMessageConverter;
import java.io.IOException;
import java.lang.reflect.Type;
import java.util.LinkedHashMap;
/**
 * 处理@RequestBody注解为String的情况,只支持接收单个参数的情况
 * Created by test
 * Date:2017/1/4
 * Time:17:33
 */
public class CustomerMappingJackson2HttpMessageConverter extends MappingJackson2HttpMessageConverter {
    @Override
    protected Object readInternal(Class<?> clazz, HttpInputMessage inputMessage) throws IOException, HttpMessageNotReadableException {
        Class<?> deseriClazz = getClazz(clazz);
        Object param = super.readInternal(deseriClazz, inputMessage);
        return getTrueObject(clazz, param);

    }

    @Override
    public Object read(Type type, Class<?> contextClass, HttpInputMessage inputMessage)
            throws IOException, HttpMessageNotReadableException {
        Type deseriType = getType(type);
        Object param = super.read(deseriType, contextClass, inputMessage);
        return getTrueObject(type, param);
    }

    /**
     * 通过返回参数类型决定是否处理参数,如果是String类型的参数,将解析后的HashMap里的值返回(只支持单个参数)
     *
     * @param type  返回参数类型
     * @param param 参数值
     * @return 实际参数值
     */
    private Object getTrueObject(Type type, Object param) {
        if (type == String.class) {
            Object backParam = null;
            if (param != null && param instanceof LinkedHashMap) {
                LinkedHashMap paramMap = (LinkedHashMap) param;
                if (paramMap.size() == 1) {
                    backParam = paramMap.get(paramMap.keySet().iterator().next());
                }
            }
            param = backParam;
        }
        return param;
    }

    /**
     * 获取解析参数用的Type
     *
     * @param type 参数类型
     * @return
     */
    private Type getType(Type type) {
        Type deseriClazz;
        if (type == String.class) {
            //jackson不支持String默认用LinkedHashMap
            deseriClazz = LinkedHashMap.class;
        } else {
            deseriClazz = type;
        }
        return deseriClazz;
    }

    /**
     * 获取解析参数用的Type
     * @param clazz 参数类型
     * @return
     */
    private Class<?> getClazz(Class<?> clazz) {
        Class<?> deseriClazz;
        if (clazz == String.class) {
            //jackson不支持String默认用LinkedHashMap
            deseriClazz = LinkedHashMap.class;
        } else {
            deseriClazz = clazz;
        }
        return deseriClazz;
    }
}

spring mvc xml配置文件修改:

<bean id="mappingJacksonHttpMessageConverter"
          class="com.test.converter.json.CustomerMappingJackson2HttpMessageConverter">
        <property name="supportedMediaTypes">
            <list>
                <value>text/html;charset=UTF-8</value>
                <value>application/json;charset=UTF-8</value>
            </list>
        </property>
    </bean>

Controller层:

@RequestMapping(value = "/delUser", method = RequestMethod.POST)
    @ResponseBody
    public JsonResult delUser(@RequestBody String id) {
    。。。
    }

 

转载于:https://my.oschina.net/u/2391658/blog/1498851

  • 0
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值