这里的主要问题是,'/test.htm'在检查Accept标头的值之前,路径将首先使用内容协商。使用扩展名*.htm,Spring将使用org.springframework.web.accept.ServletPathExtensionContentNegotiationStrategy和来确定要返回的可接受的媒体类型text/html与MappingJacksonHttpMessageConverter产生的媒体类型不匹配,即。application/json因此返回406。
一种简单的解决方案是将路径更改为,类似于/test,其中基于该路径的内容协商不会解析响应的任何内容类型。相反,ContentNegotiationStrategy基于标头的其他内容将解析标头的值Accept。
复杂的解决方案是更改处理的ContentNegotiationStrategy对象在上注册的对象的顺序。RequestResponseBodyMethodProcessor``@ResponseBody
解决方法我想从控制器发送JSON。我有以下配置。
spring-servlet.xml:
<?xml version='1.0' encoding='UTF-8'?><beans xmlns='http://www.springframework.org/schema/beans' xmlns:xsi='http://www.w3.org/2001/XMLSchema-instance' xmlns:mvc='http://www.springframework.org/schema/mvc' xmlns:context='http://www.springframework.org/schema/context' xsi:schemaLocation='http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-4.0.xsd http://www.springframework.org/schema/mvc http://www.springframework.org/schema/mvc/spring-mvc.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd'> <mvc:annotation-driven/> <mvc:resources mapping='/resources/**' location='/resources/'/> <context:component-scan base-package='com.castle.controllers'/> <bean class='org.springframework.web.servlet.view.InternalResourceViewResolver'><property name='viewClass' value='org.springframework.web.servlet.view.JstlView'/><property name='prefix' value='/views/'/><property name='suffix' value='.jsp'/> </bean></beans>
.js:
function testAjax() { var data = {userName: 'MyUsername',password:'Password'}; $.ajax({url: ’ajax/test.htm’,dataType : ’json’,type : ’POST’,contentType: 'application/json',data: JSON.stringify(data),success: function(response){ alert(’Load was performed.’);} });}
UserTest.java:
public class UserTest { private String userName; private String password; public String getUserName() {return userName; } public void setUserName(String userName) {this.userName = userName; } public String getPassword() {return password; } public void setPassword(String password) {this.password = password; }}
TestAjaxController.java:
@Controller@RequestMapping('/ajax')public class TestAjaxController { @RequestMapping(method = RequestMethod.POST,value = '/test.htm') public @ResponseBody UserTest testAjaxRequest(@RequestBody UserTest user) {return user; }}
pom.xml:
<dependency><groupId>org.codehaus.jackson</groupId><artifactId>jackson-mapper-asl</artifactId><version>1.9.13</version> </dependency> <dependency><groupId>org.codehaus.jackson</groupId><artifactId>jackson-core-asl</artifactId><version>1.9.13</version></dependency>
当我执行此请求时,我进入了表示为UserTest对象的Controller JSON。但返回时:
HTTP状态406-此请求标识的资源仅能够生成具有根据请求“接受”标头不可接受的特征的响应。
我做错了什么?我知道,关于此类情况有很多问题,但我无法在两天内解决…
更新 我已经找到了解决方案!只需要返回一个对象。不是用户对象或其他东西。但 return Object;
public @ResponseBody Object testAjaxRequest(@RequestBody UserTest user) {List<UserTest> list = new ArrayList<>();list.add(user);list.add(user);list.add(user);return list;