我想知道例如SpringMVC控制器是否可以有方法签名,例如
@RequestMapping(value = "/target", method = RequestMethod.POST)
@ResponseBody
public void acceptObject(@RequestBody MyObjectDto dto,@RequestBody String messageBody) {
//Authenticate messageBody
//Process mapped DTO
}
目的是将JSON发布到此控制器,原始消息体将进行身份验证以确保完整性,如果正确,则JSON将映射到可以切换以进行处理的DTO。
目前我最终
java.io.IOException: Stream closed
答案 0 :(得分:13)
Spring使用一个名为HandlerMethodArgumentResolver
的接口来决定它将传递给处理程序方法的参数。对于使用@RequestBody
注释的参数,它使用名为RequestResponseBodyMethodProcessor
的类。该类基本上在一组HttpMessageConverter
对象中查找可以读取请求的content-type
并可以转换为指定类型的对象。如果找到一个,它会将HttpServletRequest
的正文作为InputStream
传递给HttpMessageConverter
对象。
在这种情况下,您可能会发现一些JSON反序列化器正在工作。很可能(看到你得到的IOException
)消耗流然后关闭它。
所以这种做事的方式并不是直接可行的。
一种解决方案是在您自己的实现中创建一个Filter
来缓存HttpServletRequest
,以使其可重复使用/重新读取所需的次数。但是,从身体反序列化的规则可能会被Spring假设,而不是你想要的。在这种情况下,您可以创建自己的InputStream
和Annotation
,然后在配置中注册应用程序。然后,您可以从请求正文中精确控制事件的反序列化。
另一个解决方案是将HandlerMethodArgumentResolver
和MyObjectDto
组合到一个DTO中,如果这对您的数据模型(以及Spring反序列化过程)有意义。