spring boot 处理json4中为什么增加了关于json的处理

&&完springmvc从3.1.4.RELEASE升级到4.1.1.RELEASE版本后,ajax请求返回json时为什么报错?代码都没改动,只是spring版本做了升级,所有类似这种的springmvc方法都报错:
@RequestMapping(value = { &reminds& }, method = { RequestMethod.GET })
public @ResponseBody
JSONObject reminds(HttpServletRequest request, HttpSession session) {
JSONObject json = new JSONObject();
User user = (User) session
.getAttribute(GlobalConstants.SESSION_LOGIN_USER_NAME);
if (user == null) {
json.put(&error&, &尚未登录&);
List&ModuleDesc& remindDescs = (List&ModuleDesc&) session
.getAttribute(&remindDescs&);
json.put(&error&, &&);
json.put(&remindDescs&, remindDescs);
user.setLoginTime(new Date());
}报错截图:the server responded with a status of 406 (Not Acceptable)1个牛币所有回答列表(2)&LV4对http 406 code的解释是这样的:406 - Not AcceptableThe 406 status code means that, although the server understood and processed the request, the response is of a form the client cannot understand. A client sends, as part of a request, headers indicating what types of data it can use, and a 406 error is returned when the response is of a type not i that list.request请求header的AcceptAccept:application/json, text/javascript, */*; q=0.01但response响应header是Content-Type:text/html通过万能的stackoverflow解决了问题,不只是需要加pom
&!-- For JSON --&
&dependency&
&groupId&org.codehaus.jackson&/groupId&
&artifactId&jackson-core-asl&/artifactId&
&version&${jackson.version}&/version&
&/dependency&
&dependency&
&groupId&org.codehaus.jackson&/groupId&
&artifactId&jackson-mapper-asl&/artifactId&
&version&${jackson.version}&/version&
&/dependency&
&dependency&
&groupId&com.fasterxml.jackson.core&/groupId&
&artifactId&jackson-core&/artifactId&
&version&2.4.3&/version&
&/dependency&
&dependency&
&groupId&com.fasterxml.jackson.core&/groupId&
&artifactId&jackson-databind&/artifactId&
&version&2.4.3&/version&
&/dependency&还需要在applicationContext.xml中增加
&mvc:annotation-driven
content-negotiation-manager=&contentNegotiationManager& /&
&bean id=&contentNegotiationManager&
class=&org.springframework.web.accept.ContentNegotiationManagerFactoryBean&&
&!-- Turn off working out content type based on URL file extension, should
fall back to looking at the Accept headers --&
&property name=&favorPathExtension& value=&false& /&
&/bean&请求200正常的截图:stackoverflow地址:/questions//spring-3-x-json-status-406-characteristics-not-acceptable-according-to-the-requ最佳答案buqingchu等等等等完等完完等等等完相关问答完等完等等完完等完等等等最近浏览暂无贡献等级暂无贡献等级暂无贡献等级暂无贡献等级暂无贡献等级暂无贡献等级暂无贡献等级暂无贡献等级暂无贡献等级扫描二维码关注最代码为好友"/>扫描二维码关注最代码为好友很简单的一个东西,这里就不做过多介绍了,写一个小Demo,随手记录下。
首先,在搭好SpringMVC工程环境之后,如果想用Spring自带的Json,需要额外的添加2个JAR包:
1、jackson-core-asl-1.9.9.jar
2、jackson-mapper-asl-1.9.9.jar
我这里使用的是Maven,也相对应的给出pox.xml
&dependency&
&groupId&org.codehaus.jackson&/groupId&
&artifactId&jackson-core-lgpl&/artifactId&
&version&1.8.1&/version&
&/dependency&
&dependency&
&groupId&org.codehaus.jackson&/groupId&
&artifactId&jackson-mapper-lgpl&/artifactId&
&version&1.8.1&/version&
&/dependency&
当然也可以不使用Spring自带的Json,还有很多第三方的Json支持包,比如谷歌的Gson,都是很好用的东西。
关于Gson的使用,之前的文章里也有做介绍,请戳:《》
好了,进入正题,要使用Spring自带的Json,需要在SpringMVC配置文件里做一些配置:
&!-- 处理在类级别上的@RequestMapping注解 --&
class="org.springframework.web.servlet.mvc.annotation.DefaultAnnotationHandlerMapping" /&
&!-- 处理在方法级别上的@RequestMapping注解 --&
class="org.springframework.web.servlet.mvc.annotation.AnnotationMethodHandlerAdapter"&
&property name="messageConverters"&
class="org.springframework.http.converter.StringHttpMessageConverter"&
&property name="supportedMediaTypes"&
&!-- 默认是ISO-88859-1,避免乱码这里设置为UTF-8 --&
text/charset=UTF-8
&/property&
&!-- 启动JSON格式的配置 --&
&bean id="jacksonMessageConverter"
class="org.springframework.http.converter.json.MappingJacksonHttpMessageConverter"&
&!-- 解决 HttpMediaTypeNotAcceptableException: Could not find acceptable
representation --&
&property name="supportedMediaTypes"&
&value&application/charset=UTF-8&/value&
&/property&
&/property&
有了以上的配置之后,我们只需要在对应处理AJAX请求的方法上加上注解@ResponseBody,这样Spring就会帮我们把内容或对象作为HTTP响应的正文返回,会跳过视图处理部分,而调用适合HttpMessageConverter,将返回值(对象、字符串、List集合等)写入输出流。
SpringMVC的用法这里就不再多说了,直接给出关键代码:
//向页面直接输出Json字符串
@ResponseBody
@RequestMapping(value="/showUser",params="json",produces="application/json")
public User showUserJson(){
User user=userService.getUserById(1);//获取数据库的一条信息
@RequestMapping
value:&&&& 指定请求的实际地址,指定的地址可以是URI Template 模式(后面将会说明);
produces:&&& 指定返回的内容类型,仅当request请求头中的(Accept)类型中包含该指定类型才返回;
params: 指定request中必须包含某些参数值,才让该方法处理。
看一下页面输出:
怎么样?相比Struts2输出Json要简单的多吧,少去了很多配置和通配符的设定。
再来看一下和AJAX的配合使用,服务端的代码依旧如上,然后我们写一个JSP页面进行测试
1 &%@ page language="java" contentType="text/ charset=UTF-8"
pageEncoding="UTF-8"%&
String path = request.getContextPath();
String basePath = request.getScheme() + "://"
+ request.getServerName() + ":" + request.getServerPort()
+ path + "/";
&script type="text/javascript" src="&%=basePath %&js/jquery-1.4.4.min.js"&&/script&
&script type="text/javascript"&
$(document).ready(function(){
$("#send").click(function(){
type:"get",
url:"&%=basePath %&userController/showUser?json",
dataType:" json",
success:function(data){
alert(data);
26 &/head&
28 &h3&点击下面按钮,输出Json信息&/h3&
29 &input type="button" id="send" name="send" value="获取json信息"&
30 &/body&
31 &/html&
这里要提到一个注意事项,我们在整合SpringMVC的时候需要在web.xml进行对DispatcherServlet的配置
&!-- SpringMVC配置 --&
&servlet-name&springDispatcherServlet&/servlet-name&
&servlet-class&org.springframework.web.servlet.DispatcherServlet&/servlet-class&
&init-param&
&param-name&contextConfigLocation&/param-name&
&param-value&classpath:springmvc.xml&/param-value&
&/init-param&
&load-on-startup&1&/load-on-startup&
&/servlet&
&servlet-mapping&
&servlet-name&springDispatcherServlet&/servlet-name&
&url-pattern&/&/url-pattern&
&/servlet-mapping&
如果你配置DispatcherServlet拦截*.do就不会存在静态资源访问的问题,
但如果你和我一样配置DispatcherServlet拦截 / (所有),那么对*.js,*.css,*.jpg等资源的访问也就被拦截了,也就访问不到了。
这里顺带说下解决方法:
激活Tomcat的defaultServlet来处理静态文件&
1 &servlet-mapping&
&servlet-name&default&/servlet-name&
&url-pattern&*.jpg&/url-pattern&
4 &/servlet-mapping&
5 &servlet-mapping&
&servlet-name&default&/servlet-name&
&url-pattern&*.js&/url-pattern&
8 &/servlet-mapping&
9 &servlet-mapping&
&servlet-name&default&/servlet-name&
&url-pattern&*.css&/url-pattern&
12 &/servlet-mapping&
每种文件类型都要配置,要写在DispatcherServlet的前面, 让defaultServlet先拦截,这个就不会进入Spring了。
看下实现效果:
阅读(...) 评论()当前很多应用已经开始将响应返回为json串,所以基于springframework框架开发的服务端程序,让响应返回json字符串成为了一种常用手段。 这里介绍一下如何在spring-MVC框架下方便快捷的返回json字符串。 首先,需要在controller类的方法名头上加@ReponseBody注解,但是只增加这个注解是不够的,在使用httpclient4.5.x模拟post请求时,出现http status 406的错误:&&&
Java代码 复制代码 收藏代码
1.406 Not Acceptable 指定的资源已经找到,但它的MIME类型和客户在Accpet头中所指定的不兼容(HTTP 1.1新)
如果采用Spring-MVC框架开发,那么解决办法如下:
1)在spring-servlet.xml里增加
Java代码 复制代码 收藏代码
1.&mvc:annotation-driven&
&mvc:message-converters register-defaults="true"&
&bean class="org.springframework.http.converter.json.MappingJacksonHttpMessageConverter"
p:supportedMediaTypes="*/*" /&
&/mvc:message-converters&
6.&/mvc:annotation-driven&
2)maven项目,在pom.xml里增加
Java代码 复制代码 收藏代码
1.&dependency&
&groupId&org.codehaus.jackson&/groupId&
&artifactId&jackson-mapper-asl&/artifactId&
&version&1.9.13&/version&
5.&/dependency&
6.&dependency&
&groupId&org.codehaus.jackson&/groupId&
&artifactId&jackson-core-asl&/artifactId&
&version&1.9.13&/version&
10.&/dependency&
gradle项目,在build.gradle文件的dependencies项下增加
Java代码 复制代码 收藏代码
1.compile 'org.codehaus.jackson:jackson-mapper-asl:1.9.13'
2.compile 'org.codehaus.jackson:jackson-core-asl:1.9.13'
附:我在测试时用httpclient4.5.x模拟post请求时返回的数据
Java代码 复制代码 收藏代码
1.response.toString():
2.HttpResponseProxy{HTTP/1.1 200 OK [Server: Apache-Coyote/1.1, Content-Type: application/charset=UTF-8, Transfer-Encoding: chunked, Date: Tue, 29 Jul 2015 08:42:29 GMT]}
4.EntityUtils.toString(entity, "utf-8"):
5.{"code":0,"flag":false,"message":"用户名错误,请填写手机号码或者Email!","uid":-1,"mobile":null,"email":null,"username":null}
阅读(...) 评论()springMVC4(4)json与对象互转实例解析请求响应数据转换器 - CSDN博客
springMVC4(4)json与对象互转实例解析请求响应数据转换器
格式化数据输入输出
Spring3.0的重要接口:HttpMessageConveter为我们提供了强大的数据转换功能,将我们的请求数据转换为一个java对象,或将java对象转化为特定格式输出等。比如我们常见的从前端注册表单获取json数据并转化为User对象,或前端获取用户信息,后端输出User对象转换为json格式传输给前端等。
spring 为我们提供了众多的HttpMessageConveter实现类,其中我们可能用得最多的三个实现类是:
FormHttpMessageConverter
从请求和响应读取/编写表单数据。默认情况下,它读取媒体类型 application/x-www-form-urlencoded 并将数据写入MultiValueMap&String,String&
MarshallingHttpMessageConverter
使用 Spring 的 marshaller/un-marshaller 读取/编写 XML 数据。它转换媒体类型为 application/xml
MappingJacksonHttpMessageConverter
使用 Jackson 的 ObjectMapper 读取/编写 JSON 数据。它转换媒体类型为application/json
转换器的装配方式有两种,一种是通过注册org.springframework.web.servlet.mvc.annotation.AnnotationMethodHandlerAdapter来装配messageConverters,如下所示:
class="org.springframework.web.servlet.mvc.annotation.AnnotationMethodHandlerAdapter"&
name="messageConverters"&
bean="jsonConverter" /&
id="jsonConverter" class="org.springframework.http.converter.json.MappingJacksonHttpMessageConverter"&
name="supportedMediaTypes" value="application/json" /&
另一种是启用注解&mvc:annotation-driven /&
该注解会会初始化7个转换器:
- ByteArrayHttpMessageConverter
- StringHttpMessageConverter
- ResourceHttpMessageConverter
- SourceHttpMessageConverter
- XmlAwareFormHttpMessageConverter
- Jaxb2RootElementHttpMessageConverter
- MappingJacksonHttpMessageConverter
通过以上两种方法,我们即可完成我们的转换器注册。
但我们想要在控制层完成数据的输入输出转换,需要通过下列途径:
1. 使用@RequestBody和@ResponseBody对处理方法进行标注。其中@RequestBody通过合适的HttpMessageConverter将HTTP请求正文转换为我们需要的对象内容。而@ResponseBody则将我们的对象内容通过合适的HttpMessageConverter转换后作为HTTP响应的正文输出。
2. 使用HttpEntity、ResponseEntity作为处理方法的入参或返回值
通过以上讲解,我们已经有足够的知识准备,来完成我们的实例:将json数据转换为合适的java对象输入,并将java对象转换为符合格式的json字符输出:
1. 导入需要的jar包
装配MappingJacksonHttpMessageConverter需要我们的jackson相关jar包,我们使用maven来管理项目,在pom.xml中配置如下信息:
&org.codehaus.jackson&
&jackson-core-asl&
&org.codehaus.jackson&
&jackson-mapper-asl&
2. 装配MappingJacksonHttpMessageConverter
这里我们使用上面提到的方式二更为便利,在spring容器中加入:
&mvc:annotation-driven /&
关于springMVC所需的其他配置,可参考我的另一篇文章,或通过文尾的源码下载获取
3. 编写测试文件
下面是我们的User POJO测试类
public class User {
private String userN
public String toString() {
return "User [id=" + id + ", userName=" + userName + ", password="
+ password + "]";
下面是我们的控制层测试文件:
@Controller
@RequestMapping("/user")
public class UserController {
@RequestMapping("getUser")
public void getUser( @RequestBody User user){
System.out.println(user);
@RequestMapping("getUser1")
public void getUser1( HttpEntity&User& userEntity){
System.out.println(userEntity.getBody());
@ResponseBody
@RequestMapping("getUser2")
public User getUser2(User user){
System.out.println(user);
@RequestMapping("getUser3")
public HttpEntity&User& getUser3(User user){
System.out.println(user);
HttpEntity&User& uEntity = new HttpEntity&User&(user);
上面分别展示了注解和HttpEntity的用法。关于HttpResponse只是在HtppEntity的基础上进一步对相应信息进行封装,如修改一些相应头信息等
关于以上的getUser()getUser1()能将我们的json字符串转换为相应的对象,我们可以任何参数名输入:
{“id”:10,”password”:”myPassword”,”userName”:”myUserName”}
在这里我们需要的是需将请求头的contentType设置为”application/UTF-8“。这样spring才能找到对应的json解析器对我们的json字符串进行解析。否则会报错误:415 Unsupported Media Type
程序中方法调用User的toString()在控制台打印字段:
User [id=10, userName=asd, password=qwe]
对于以上的getUser2()和getUser3()方法,我们访问如:
http://localhost:8080/springMVC/user/getUser3?id=10&password=qwe&userName=asd。然后spring会帮我们自动将参数对应User对象的属性名绑定到方法入参的user对象中(关于复杂对象、集合绑定可参考我后面系列的文章)。根据上面url传入的参数,spring自动将我们的User对象转换为json格式字符串输出,内容如下:
{"id":10,"userName":"asd","password":"qwe"}
选择合适的数据转换器
在前面讲解中,我们通过AnnotationMethodHandlerAdapter注册了众多的数据转换器,而spring会针对不同的请求响应媒体类型,spring会为我们选择最恰当的数据转换器,它是按以下流程进行寻找的:
首先获取注册的所有HttpMessageConverter集合
然后客户端的请求header中寻找客户端可接收的类型,比如
Accept application/json,application/xml等,组成一个集合
所有的HttpMessageConverter 都有canRead和canWrite方法 返回值都是boolean,看这个HttpMessageConverter是否支持当前请求的读与写,读对应@RequestBody注解, 写对应@ResponseBody注解
遍历HttpMessageConverter集合与前面获取可接受类型进行匹配,如果匹配直接使用当前第一个匹配的HttpMessageConverter,然后return(一般是通过Accept和返回值对象的类型进行匹配)
本例的示例代码可到的mvc_messageConvertor1文件夹中下载
本文已收录于以下专栏:
相关文章推荐
1.springmvc默认使用jackson来实现对象与json之间的相互转换的。在转换之前我需要引入两个springMVC依赖的两个jar包:
 jackson-core-asl(jackson核...
springmvc使用json类自动转换
springmvc controller中return对象转json
由于快过年的原因,项目组没有太多任务,闲来无事研究了一下spring中restful调用。发现spring竟然已经强大到如此境界,程序员已经不需要在关心在写接口的过程中数据的转换以及调用,只需要专注业...
有时候希望Spring在controller中自动将组装好的消息对象转换为JSON格式输出
1. 采用全注解配置
&beans xmlns=&http://www.s...
从|Spring3.1之后,开始推荐使用RequestMappingHandlerMapping和RequestMappingHandlerAdapter来进行方法映射,
在controller里支...
SpringMVC接口输出JSON数据
有效选择七个关于Java的JSON开源类库
April 4, ;By Constantin Marian Alin
翻译:无若
 (英语原文:/...
一、过程(存储过程)
与过程相比,存储过程是在数据库中的一个对象,如果编译错误。
可以用show errors or show err
现在定义一个简单的过程...
在写这个存储过程的时候自己只是对存储过程有一个简答的编程理解,觉得应该和大多数编程语言没什么区别吧,就试试喽
先说说需求吧!
1、首先我需要获取表空间中的所有表名,并动态的去搜索遍历,所以不得不用...
他的最新文章
讲师:吴岸城
您举报文章:
举报原因:
原文地址:
原因补充:
(最多只允许输入30个字)spring mvc 输出 json 异常处理
我的图书馆
spring mvc 输出 json 异常处理
上一篇写了JSON支持,请求成功时,AnnotationMethodHandlerAdapter使用messageConverters将方法返回值输出到客户端。
如果请求失败呢?根本就没有返回值,怎么输出?
这种情况,这需要使用spring的错误解析器(ExceptionResolver)。当Controller发生异常,ExceptionResolver将被调用,如此便可以对上面的情况进行处理。
我们本来想使用spring的org.springframework.web.servlet.mvc.annotation.AnnotationMethodHandlerExceptionResolver,很遗憾,这个错误解析器有bug,而且功能有缺陷,因此需要我们自己去实现一个ExceptionResolver。
这个bug难以描述,感兴趣的可以找出bug,去它WIKI提出,本人英文太烂,根本不会写.........。
实现ExceptionResolver的思路:
目前的异常处理:大部分的做法是在Controller中进行try...catch,try中处理正常请求,catch中处理异常请求。缺点:
1、每个方法都要这么写,代码重复。
2、捕获不到Controller外部的错误,例如某个拦截器的错误,这时将无法给客户一个有好的提示。
3、需要在catch语句块中记录日志,代码重复。
这个错误解析器应该有如下功能:
1、既然使用异常解析器,那么就不必在Controller中对异常进行处理,抛出即可,简化开发,异常统一控制。
2、ajax请求(有@ResponseBody的Controller)发生错误,输出JSON。
3、页面请求(无@ResponseBody的Controller)发生错误,输出错误页面。
4、它需要与AnnotationMethodHandlerAdapter使用同一个messageConverters
5、异常处理细节可控制。
AnnotationHandlerMethodExceptionResolver ,这是我写的实现类。用法:
[java] /**&&*&不必在Controller中对异常进行处理,抛出即可,由此异常解析器统一控制。&br&&&*&ajax请求(有@ResponseBody的Controller)发生错误,输出JSON。&br&&&*&页面请求(无@ResponseBody的Controller)发生错误,输出错误页面。&br&&&*&需要与AnnotationMethodHandlerAdapter使用同一个messageConverters&br&&&*&Controller中需要有专门处理异常的方法。&&*&&&*&@author&dongjian&&*&&&*&*/&&public&class&AnnotationHandlerMethodExceptionResolver&extends&ExceptionHandlerExceptionResolver&{&&&&&&&&&&&&private&String&defaultErrorV&&&&&&&&&&&&public&String&getDefaultErrorView()&{&&&&&&&&&&return&defaultErrorV&&&&&&}&&&&&&&&public&void&setDefaultErrorView(String&defaultErrorView)&{&&&&&&&&&&this.defaultErrorView&=&defaultErrorV&&&&&&}&&&&&&&&protected&ModelAndView&doResolveHandlerMethodException(HttpServletRequest&request,&HttpServletResponse&response,&HandlerMethod&handlerMethod,&Exception&exception)&{&&&&&&&&&&&&&&&&&&&&if&(handlerMethod&==&null)&{&&&&&&&&&&&&&&return&&&&&&&&&&&}&&&&&&&&&&&&&&&&&&&&Method&method&=&handlerMethod.getMethod();&&&&&&&&&&&&if&(method&==&null)&{&&&&&&&&&&&&&&return&&&&&&&&&&&}&&&&&&&&&&&&&&&&&&&&ModelAndView&returnValue&=&super.doResolveHandlerMethodException(request,&response,&handlerMethod,&exception);&&&&&&&&&&&&&&&&&&&&ResponseBody&responseBodyAnn&=&AnnotationUtils.findAnnotation(method,&ResponseBody.class);&&&&&&&&&&if&(responseBodyAnn&!=&null)&{&&&&&&&&&&&&&&try&{&&&&&&&&&&&&&&&&&&ResponseStatus&responseStatusAnn&=&AnnotationUtils.findAnnotation(method,&ResponseStatus.class);&&&&&&&&&&&&&&&&&&if&(responseStatusAnn&!=&null)&{&&&&&&&&&&&&&&&&&&&&&&HttpStatus&responseStatus&=&responseStatusAnn.value();&&&&&&&&&&&&&&&&&&&&&&String&reason&=&responseStatusAnn.reason();&&&&&&&&&&&&&&&&&&&&&&if&(!StringUtils.hasText(reason))&{&&&&&&&&&&&&&&&&&&&&&&&&&&response.setStatus(responseStatus.value());&&&&&&&&&&&&&&&&&&&&&&}&else&{&&&&&&&&&&&&&&&&&&&&&&&&&&try&{&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&response.sendError(responseStatus.value(),&reason);&&&&&&&&&&&&&&&&&&&&&&&&&&}&catch&(IOException&e)&{&}&&&&&&&&&&&&&&&&&&&&&&}&&&&&&&&&&&&&&&&&&}&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&return&handleResponseBody(returnValue,&request,&response);&&&&&&&&&&&&&&}&catch&(Exception&e)&{&&&&&&&&&&&&&&&&&&return&&&&&&&&&&&&&&&}&&&&&&&&&&}&&&&&&&&&&&&&&&&&&&&if(returnValue.getViewName()&==&null){&&&&&&&&&&&&&&returnValue.setViewName(defaultErrorView);&&&&&&&&&&}&&&&&&&&&&&&&&&&&&&&return&returnV&&&&&&&&&&&&&&&&}&&&&&&&&&&&&&&&&&&@SuppressWarnings({&"unchecked",&"rawtypes"&})&&&&&&private&ModelAndView&handleResponseBody(ModelAndView&returnValue,&HttpServletRequest&request,&HttpServletResponse&response)&throws&ServletException,&IOException&{&&&&&&&&&&Map&value&=&returnValue.getModelMap();&&&&&&&&&&HttpInputMessage&inputMessage&=&new&ServletServerHttpRequest(request);&&&&&&&&&&List&MediaType&&acceptedMediaTypes&=&inputMessage.getHeaders().getAccept();&&&&&&&&&&if&(acceptedMediaTypes.isEmpty())&{&&&&&&&&&&&&&&acceptedMediaTypes&=&Collections.singletonList(MediaType.ALL);&&&&&&&&&&}&&&&&&&&&&MediaType.sortByQualityValue(acceptedMediaTypes);&&&&&&&&&&HttpOutputMessage&outputMessage&=&new&ServletServerHttpResponse(response);&&&&&&&&&&Class&?&&returnValueType&=&value.getClass();&&&&&&&&&&List&HttpMessageConverter&?&&&messageConverters&=&super.getMessageConverters();&&&&&&&&&&if&(messageConverters&!=&null)&{&&&&&&&&&&&&&&for&(MediaType&acceptedMediaType&:&acceptedMediaTypes)&{&&&&&&&&&&&&&&&&&&for&(HttpMessageConverter&messageConverter&:&messageConverters)&{&&&&&&&&&&&&&&&&&&&&&&if&(messageConverter.canWrite(returnValueType,&acceptedMediaType))&{&&&&&&&&&&&&&&&&&&&&&&&&&&messageConverter.write(value,&acceptedMediaType,&outputMessage);&&&&&&&&&&&&&&&&&&&&&&&&&&return&new&ModelAndView();&&&&&&&&&&&&&&&&&&&&&&}&&&&&&&&&&&&&&&&&&}&&&&&&&&&&&&&&}&&&&&&&&&&}&&&&&&&&&&if&(logger.isWarnEnabled())&{&&&&&&&&&&&&&&logger.warn("Could&not&find&HttpMessageConverter&that&supports&return&type&["&+&returnValueType&+&"]&and&"&+&acceptedMediaTypes);&&&&&&&&&&}&&&&&&&&&&return&&&&&&&}&&&&}&&
------------------------web.xml-------------------------------------
spring mvc当然会自动注册一些异常解析器,我们需要禁止自动注册,让其使用我们自定义的类。
&servlet-name&dispatcher&/servlet-name&
&servlet-class&org.springframework.web.servlet.DispatcherServlet&/servlet-class&
&init-param&
&param-name&contextConfigLocation&/param-name&
&param-value&classpath:dispatcher-servlet.xml&/param-value&
&/init-param&
&init-param&
&param-name&detectAllHandlerExceptionResolvers&/param-name&&!-- 取消其自动注册的异常解析器 --&
&param-value&false&/param-value&
&/init-param&
&load-on-startup&1&/load-on-startup&
&/servlet&
---------------------------spring mvc配置 -------------------------------------------
&!-- 由于取消自动注册,DispatcherServlet会在spring上下文寻找 id 为 handlerExceptionResolver作为异常解析器 --&
&bean id="handlerExceptionResolver" class="com.mon.web.AnnotationHandlerMethodExceptionResolver"&
&property name="defaultErrorView" value="error.vm"/&&!-- 错误页面 --&
&property name="messageConverters" ref="messageConverters"/& &!--见上一篇,有定义过,标有@ResponseBody被此messageConverters输出--&
-------------------------------BaseController 代码-------------------------------------------
所有Controller继承BaseController
* 异常控制,这便是异常细节可控,将来可用于支持国际化(异常信息国际化)
@ExceptionHandler(Exception.class)
@ResponseStatus(value=HttpStatus.INTERNAL_SERVER_ERROR)
public ModelAndView handleException(Exception ex, HttpServletRequest request) {
return new ModelAndView().addObject("error", "错误信息");
---------------------error.vm代码---------------------
OK,到现在就可以了。下面让我们测试一下预期功能。
------------------------------测试代码DemoController extends BaseController --------------------------------------------
@RequestMapping("/demoAjax")
@ResponseBody
public Map demoAjax(String name) {
if(StringUtils.isEmpty(name) ) throw new RuntimeException();
return Collections.singletonMap("name", name);
@RequestMapping("/demoPage")
public ModelAndView demoPage(String name) {
if(StringUtils.isEmpty(name) ) throw new RuntimeException();
ModelAndView mav = new ModelAndView();
mav.setViewName("demo.vm");
---------------------------测试代码之前端------------------------------
$.ajaxSetup({ //设置ajax请求全局默认设置
async : true,
error : function(jqXHR, textStatus, errorThrown){
var msg = $.parseJSON(jqXHR.responseText).
alert(msg);
traditional : true,
dataType : "json",
type : "POST"
$.ajax({ //请求将成功
url: "demoAjax.action",
data: {name: "you param"},
dataType : "json",
type : "POST",
success: function(data){
alert("请求发送成功,返回数据:" + data.name);
$.ajax({ //请求将失败,弹出人性化的错误信息
url: "demoAjax.action",
dataType : "json",
type : "POST",
success: function(data){
alert("请求发送成功,返回数据:" + data.name);
&a href="demoPage.action?name=you name"&将返回demo页面&/a&
&a href="demoPage.action"&将返回错误页面&/a&
到此异常处理完成。
我们不必在程序中对异常进行处理,不管三七二十一,全部抛出即可,代码大大简化。
请求处理情况如下:
ajax请求:正常时,使用@ResponseBody输出。错误时,返回错误的JSON串。
页面请求:正常时进入该页面,当请求发生异常时,返回错误页面。
不用编码处理JSON和异常处理
TA的最新馆藏
喜欢该文的人也喜欢

我要回帖

更多关于 spring mvc json 的文章

 

随机推荐