resumen
SpringMVC utiliza el convertidor de mensajes para realizar una conversión automática entre mensajes de solicitud y objetos, objetos y mensajes de respuesta.
En SpringMVC, puede usar las dos anotaciones @RequestBody y @ResponseBody para completar la conversión de mensajes de solicitud a objetos y objetos a mensajes de respuesta respectivamente. El mecanismo de conversión de mensajes flexible subyacente es el recientemente introducido httpmessageConverter, el mecanismo de convertidor de mensajes, que es el recientemente introducido HTTPMessageConverter en la primavera 3.x.
La abstracción de la solicitud #HTTP aún debe volver a la solicitud de solicitud, es decir, analizar el cuerpo de la solicitud y luego devolver el mensaje de respuesta. Este es el proceso de solicitud HTTP más básico. Sabemos que en el estándar de servlet, se pueden utilizar los siguientes métodos en la interfaz javax.servlet.servletRequest:
Public ServletInputStream getInputStream () lanza IOException;
Para obtener un servletinputstream. En este servletInputStream, se pueden leer todos los contenidos de un mensaje de solicitud sin procesar. Del mismo modo, en la interfaz javax.servlet.servletResponse, se pueden usar los siguientes métodos:
Public ServLetOutputStream GetOutputStream () lanza IOException;
Para obtener un ServLetOutputStream, este ServLetOutputSteam, heredado de OutputStream en Java, le permite emitir el contenido del paquete de respuesta HTTP.
Intentemos pensar como el diseñador de SpringMVC. Sabemos que los paquetes de solicitud y respuesta HTTP son esencialmente una cadena de cadenas. Cuando el paquete de solicitud llegue al mundo de Java, se encapsulará en un flujo de entrada ServletInputStream para que podamos leer los paquetes. El mensaje de respuesta se emite a través de la transmisión de salida de un ServLetOutputStream.
Solo podemos leer el mensaje de cadena original de la transmisión, y de manera similar, solo podemos escribir los caracteres originales en la transmisión de salida. En el mundo de Java, el procesamiento de la lógica de negocios se basa en objetos específicos del negocio como dimensiones de procesamiento. Luego, cuando el mensaje llega a SpringMVC y sale de SpringMVC, hay un problema de impedancia entre las cadenas y los objetos Java. Este proceso no puede convertir manualmente por el desarrollador. Sabemos que en Struts2, el OGNL se usa para lidiar con este problema, mientras que en SpringMVC, es el mecanismo httpmessageConverter. Veamos primero las dos interfaces.
#HttpinputMessage Esta clase es una abstracción de un mensaje de solicitud HTTP dentro de SpringMVC. En el método Read () del httpMessageConverter, hay un parámetro formal de httpinputMessage, que es la abstracción interna del "mensaje de solicitud" del receptor utilizado por el convertidor de mensajes de SpringMVC. El convertidor de mensajes extrae mensajes del "mensaje de solicitud" de acuerdo con las reglas y los convierte en objetos declarados en el parámetro formal del método.
paquete org.springframework.http; import java.io.ioexception; import java.io.inputstream; interfaz pública httpinputMessage extiende httpmessage {inputStream getBody () lanza IOException;}#HttpoutputMessage Esta clase es una abstracción del mensaje de respuesta HTTP dentro de SpringMVC. En el método Write () de HttpMessageConverter, hay un parámetro formal de httpoutputMessage, que es la abstracción interna del "mensaje de respuesta" del receptor utilizado por el convertidor de mensajes de SpringMVC. El convertidor de mensajes escribe el "mensaje de respuesta" en el mensaje de respuesta de acuerdo con ciertas reglas.
paquete org.springframework.http; import java.io.ioexception; import java.io.outputstream; interfaz pública httpoutputMessage extiende httpmessage {outputStream getBody () lanza IOException;}#HttpMessageConverter La abstracción de la interfaz de nivel más alto del convertidor de mensajes describe las características generales de un convertidor de mensajes. Podemos entender el proceso de pensamiento de los diseñadores Spring3.x en este mecanismo de los métodos definidos en esta interfaz.
paquete org.springframework.http.converter; import java.io.ioexception; import java.util.list; import org.springframework.http.httpinputMessage; import org.springfringframework.htttputputputmessage; import HttpMessageConverter <t> {boolean Canread (class <?> Clazz, Mediatype Mediatype); Boolean CanWrite (clase <?> Clazz, Mediatype Mediatype); Lista <Mediatype> GetSupportedMediatyPes (); T read (clase <? Extiende t> clazz, httpinputMessage inputMessage) lanza ioexception, httpmessageNotreadableException; Void Write (T T, Mediatype ContentType, httpoutputMessage outputMessage) lanza ioexception, httpmessagenotwritableException;}La definición de la interfaz httpmessageConverter ha emparejado los métodos Canread (), Read () y CanWrite (), Write (). Mediatype es la encapsulación del atributo de tipo de medios solicitado. Por ejemplo, cuando declaramos el siguiente método de procesamiento.
@RequestMapping (valor = "/cadena", método = requestmethod.post) public @ResponseBody String ReadString (@RequestBody String String) {return "Read String '" + String + "'";}Antes de que SpringMVC ingrese al método ReadString, seleccionará la clase de implementación HTTPMessageConver de HTTPMess apropiada de acuerdo con la anotación @RequestBody para analizar los parámetros de solicitud en la variable de cadena. Específicamente, se usa la clase StringHttpMessageConverter. Su método Canread () devuelve verdadero, y luego su método Read () leerá los parámetros de solicitud de la solicitud y se unirá a la variable de cadena del método ReadString ().
Cuando SpringMVC ejecuta el método ReadString, ya que el valor de retorno identifica @ResponseBody, SpringMVC usará el método Write () de StringHttpMessageConverter y escribirá el resultado como el valor de cadena en el mensaje de respuesta. Por supuesto, el método CanWrite () devuelve verdadero en este momento.
Podemos usar la siguiente figura para describir brevemente este proceso.
#RequestresponseBodyMethodProcessor Una clase descrita en el conjunto de procesos anterior es org.springframework.web.servlet.mvc.method.annotation.requestresponseBodyMethodProcessor. Esta clase implementa tanto las interfaces HandlermethodargumentResolver como las interfaces HandlermethodreturnueHandler. La primera es una interfaz de política que une el mensaje de solicitud a los parámetros formales del método de procesamiento, y la segunda es una interfaz de política que procesa el valor de retorno del método de procesamiento. Los códigos de origen de las dos interfaces son los siguientes:
paquete org.springframework.web.method.support; import org.springframework.core.methodparameter; import org.springframework.web.bind.webdatabinder; import org.springframework.web.bind.support.webdatabinderfactory; import org.springframework.web.context.request.nativeWebRequest; interfaz pública handlermethodargumentResolver {boolean sportsParameter (parámetro MethodParameter); Object resolveArgument(MethodParameter parameter, ModelAndViewContainer mavContainer, NativeWebRequest webRequest, WebDataBinderFactory bindFactory) throws Exception;}package org.springframework.web.method.support;import org.springframework.core.MethodParameter;import org.springframework.web.context.request.nativewebRequest; interfaz pública handlermethodretRoNValueHandler {boolean sportsReturnType (MethodParameter ReturnType); void handlereturnValue (Object ReturnValue, MethodParameter ReturnType, ModelAndViewContainer MavContainer, NativeWebRequest WebRequest) arroja excepción;}La clase SoldResponseBodyMethodProcessor también sirve como dos roles: análisis de parámetros de método y procesamiento de valor de retorno. De su código fuente, podemos encontrar la implementación del método de las dos interfaces anteriores.
Implementación de la interfaz handlermethodargumentResolver:
Public Boolean SupportSParameter (MethodParameter Parameter) {return Parameter.hasParameterAnnotation (requestBody.class);} public objeto resolVearGument (MethodParameter Parameter, ModelAndViewContainer mavContainer, nationWebRequest WebRequest, WebRequestFactorTorFactoryFactory) lanza Exception {Object Argumento = ReadwithMess (ReadwithMess (ReadWithMes parámetro, parámetro.getGenericParametertype ()); Name de cadena = convenciones.getVariaBlenameForParameter (parámetro); WebDatabinder Binder = bindFactory.CreateBinder (WebRequest, argumento, nombre); if (argumento! = null) {validate (aglutinante, parámetro); } mavContainer.Addattribute (bindingResult.model_key_prefix + name, binder.getBindingResult ()); argumento de retorno;}Implementación de la interfaz handlermethodreturnValueHandler
Public Boolean SupportSreturnType (MethodParameter ReturnType) {return returnType.getMethodannotation (ResponseBody.Class)! = NULL;} public void HandlerETRETURNVALUE (Object ReturnValue, MethodParameter returnType, modelandViewContainer mavcontainer, nation webrequest) lanzamiento de iMequest). HttpmediatypenotaceptableException {mavcontainer.setRequestHandled (true); if (returnValue! = null) {writeWithMessageConverters (returnValue, returnType, webRequest); }}Después de leer el código anterior, todo el contexto de conversión de mensajes HTTPMessageConverter ya está muy claro. Debido a que la implementación de las dos interfaces se basa en si existe @RequestBody y @ResponseBody como condición, y luego HttpMessageConverter se llama respectivamente para leer y escribir mensajes.
Si desea preguntar cómo rastrear el requestsponseBodyMethodProcessor, siga las ideas de las publicaciones de blog anteriores y luego vaya a Spring-MVC-Showcase para descargar el código fuente y depurar los ejemplos relacionados con HttpMessageConverter. Mientras esté dispuesto a trabajar duro, creo que definitivamente ganará el tuyo.
#Yando a Zhang Xiaolong cuando se habla de la esencia de WeChat, dijo: "WeChat es solo una plataforma y los mensajes circulan en ella". En nuestro proceso de análisis del código fuente de SpringMVC, podemos entender verdades similares del mecanismo HTTPMessageConverter. A los ojos de los diseñadores de SpringMVC, un mensaje de solicitud y un mensaje de respuesta se abstraen en un mensaje de solicitud httpinputMessage y un mensaje de respuesta httpoutputMessage, respectivamente.
Al procesar una solicitud, el convertidor de mensajes apropiado vincula el mensaje de solicitud a un objeto de parámetro formal en el método. Aquí, puede haber múltiples formularios de mensajes diferentes para el mismo objeto, como JSON y XML. Del mismo modo, al responder a una solicitud, el valor de retorno del método también puede devolverse a diferentes formularios de mensajes, como JSON y XML.
En SpringMVC, tenemos diferentes clases de implementación de HttpMessageConverter para manejar varios formularios de mensajes para diferentes formularios de mensajes. Sin embargo, siempre que la "información válida" contenida en estos mensajes sea consistente, varios convertidores de mensajes generarán el mismo resultado de conversión. En cuanto a las diferencias en los detalles de análisis entre varios mensajes, se bloquean en diferentes clases de implementación de HTTPMessageConverter.
Lo anterior es todo el contenido de este artículo. Espero que sea útil para el aprendizaje de todos y espero que todos apoyen más a Wulin.com.