java - requestbody - spring boot receive json
Spring-MVC 406 no es aceptable en lugar de JSON Response (5)
Estoy tratando de devolver una respuesta JSON con Spring 3.0.6, pero recibo una respuesta 406 "No aceptable", con la descripción: "El recurso identificado por esta solicitud solo es capaz de generar respuestas con características no aceptables de acuerdo con la solicitar encabezados "aceptar" () ".
Sé que se me ha hecho una pregunta muy similar antes, pero no puedo hacer que funcione para mi proyecto, a pesar de muchas pruebas y no entiendo lo que estoy haciendo mal.
En mi Maven pom.xml tengo lo siguiente:
<dependency>
<groupId>org.codehaus.jackson</groupId>
<artifactId>jackson-mapper-asl</artifactId>
<version>1.8.5</version>
<scope>compile</scope>
</dependency>
<dependency>
<groupId>org.codehaus.jackson</groupId>
<artifactId>jackson-core-asl</artifactId>
<version>1.8.5</version>
<scope>compile</scope>
</dependency>
En web.xml, hago referencia a webmvc-config.xml y el registro confirma que está cargado.
<servlet>
<servlet-name>mainServlet</servlet-name>
<servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
<init-param>
<param-name>contextConfigLocation</param-name>
<param-value>/WEB-INF/spring/webmvc-config.xml</param-value>
</init-param>
<load-on-startup>1</load-on-startup>
</servlet>
En webmvc-config.xml tengo lo siguiente:
<bean class="org.springframework.web.servlet.view.InternalResourceViewResolver">
<property name="prefix" value="/WEB-INF/jsp/" />
<property name="suffix" value=".jsp" />
</bean>
<mvc:annotation-driven />
Mi controlador es:
@Controller
public class ClassifiedController {
@RequestMapping(value = "/classified/{idClassified}", headers = "Accept=*/*",
method = RequestMethod.GET)
@ResponseBody
public final Classified getClassified(@PathVariable final int idClassified) {
...
Intenté con o sin el parámetro headers con los mismos resultados. Si llamo a la URL directamente con Firefox, los encabezados de solicitud contienen lo siguiente (marcado con Firebug):
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8
Si utilizo el siguiente JQuery:
$.ajax({
url: ''/classified/38001'',
type: ''GET'',
dataType: ''json''
});
Se envían los siguientes encabezados:
Accept: application/json, text/javascript, */*; q=0.01
En ambos casos, el resultado es un error 406. No sé qué más debo verificar para que funcione.
ACTUALIZACIÓN : Decidí depurar a través de Spring y descubrí que Jackson se llamó correctamente y en org.codehaus.jackson.map.ser.StdSerializerProvider el método _findExplicitUntypedSerializer contiene el siguiente código:
try {
return _createAndCacheUntypedSerializer(runtimeType, property);
} catch (Exception e) {
return null;
}
Esto es desafortunado porque oculta la fuente del problema. Con el depurador descubrí que esa excepción contenía un mensaje de error muy descriptivo:
Conflicting getter definitions for property "reminded":
ClassifiedImpl#isReminded(0 params) vs
ClassifiedImpl#getReminded(0 params)
Ahora que veo el mensaje de error es un error tonto y fácil de arreglar, pero sin eso no era tan obvio. De hecho, solucionar el problema, condujo a una serialización de trabajo.
Agregue lo siguiente en DispatcherServlet-servlet.xml.
<bean id="jacksonMessageConverter" class="org.springframework.http.converter.json.MappingJacksonHttpMessageConverter"></bean>
<bean class="org.springframework.web.servlet.mvc.annotation.AnnotationMethodHandlerAdapter">
<property name="messageConverters">
<list>
<ref bean="jacksonMessageConverter"/>
</list>
</property>
</bean>
En términos del procesamiento de MappingJacksonJson , deberá asegurarse de que Jackson ObjectMapper admita su tipo de objeto para la serialización.
Me encontré con el mismo error (406: contenido no aceptable) con la anotación Spring MVC y @RestController.
El controlador de Spring:
@RequestMapping(value = "/stuff-acknowledgment/{id}", produces ="application/json;charset=UTF-8", headers="Accept=*")
public Message acknowledgeStuff(@PathVariable("id") String id, @ModelAttribute("ack") AckBean acquittement) {
Observación:
- el URI tiene la forma:
http://www.host.com/stuff-acknowledgment/{id}
- PERO
$id
tiene un formato muy particular:xxxcomplicatedhashxxx.png
(o cualquier extensión que se te ocurra).
Por lo tanto:
Spring MVC interpreta la extensión y desea producir un resultado del mismo tipo mime (incluso si lo defino como una variable de ruta), aquí un tipo MIME "image/png"
incluso si le digo que produzca JSON. Entonces se lanza una excepción 406.
Fijar:
Elimine la extensión ".png"
en el URI, o elimine el PathVariable y colóquelo en el cuerpo, o agregue un sufijo detrás de la rutaVariable (no probado, pero debería funcionar también), el punto es evitar una extensión de archivo al final de la URI.
PD: Sé que no responde el problema específico (con la solución en la actualización) en la pregunta, pero encontré ese SO en la búsqueda de ese problema y escribí mi corrección aquí para el registro, con la esperanza de que pueda ayudar a alguien en el futuro.
Me encontré con este problema porque los objetos que quería devolver como JSON no tenían ningún método getter para sus propiedades. Jackson probablemente necesite estos. Después de agregarlos funcionó.
aunque este hilo es un poco viejo ...
necesitas agregar lo siguiente (dependencia de maven):
org.codehaus.jacksonjackson-mapper-asl1.9.13