我想找到使用 Spring Integration HTTP 和 Spring MVC 来管理入站请求的最佳方法。
我的<int-http:inbound-gateway>
配置如下:
<!-- CHANNEL -->
<int:channel id="requestChannel">
<int:dispatcher task-executor="executor"/>
</int:channel>
<int:channel id="outputChannel" />
<!-- INBOUND GATEWAY -->
<int-http:inbound-gateway id="gateway" request-channel="requestChannel"
path="/service/**"
supported-methods="POST"
reply-channel="outputChannel"
header-mapper="headerMapper">
</int-http:inbound-gateway>
<!-- SERVICE ACTIVATOR -->
<int:service-activator id="channelServiceActivator"
ref="channelService"
input-channel="requestChannel"
output-channel="outputChannel"
method="manage"/>
<bean id="channelService"
class="test.spring.data.rest.xml.channel.ChannelService"/>
通过此集成,在路径URI /service/**
上进行的每个HTTP调用都在manage()
类的“ChannelService
”方法中处理。 / p>
这是ChannelService
类:
public class ChannelService {
public void manage(Message<?> message){
// how to get the HttpServletRequest request here ???
}
}
它的工作原理:正确执行“manage()”方法,并且消息包含正确的有效负载。 但是有一个问题:我没有对ServiceChannel 中输入中收到的HttpServletRequest的任何引用。
如果我使用@Controller
的Spring MVC,我可以使用相对@RequestMapping
处理每个请求。
如果我想读取请求中包含的有效负载,我必须从HttpServletRequest的inputStream中读取它。在任何地方,我都没有机会在频道中传递消息:
@Controller
@RequestMapping(value="/service")
public class ServiceController {
@RequestMapping(value="/**")
public handle(HttpServletRequest request) throws Exception{
// how to get the Message<?> message passed on the channel here ???
}
}
如果我同时使用(@Controller
和inbound-gateway
), @Controller映射会胜过入站网关:没有机会如果存在,则处理带有inbound-gateway
的servlet路径URI
一个映射相同路径URI的@Controller
。
所以,我想了解是否有某种方法可以在@Controller中使用Message<?> message
,或者在ServiceActivator中使用HttpServletRequest,或者以其他方式来管理这种情况。
提前致谢。
答案 0 :(得分:3)
您可以通过HttpServletRequest
(http://docs.spring.io/spring-integration/reference/html/http.html#_uri_template_variables_and_expressions)访问MessageHeaders
。
HttpRequestHandlingEndpointSupport
的逻辑如下:
evaluationContext.setVariable("requestAttributes", RequestContextHolder.currentRequestAttributes());
MultiValueMap<String, String> requestParams = this.convertParameterMap(servletRequest.getParameterMap());
evaluationContext.setVariable("requestParams", requestParams);
evaluationContext.setVariable("requestHeaders", new ServletServerHttpRequest(servletRequest).getHeaders());
因此,您可以使用以下子元素配置<int-http:inbound-gateway>
:
<int-http:header name="requestAttributes" expression="#requestAttributes"/>
<int-http:header name="requestParams" expression="#requestParams"/>
<int-http:header name="requestHeaders" expression="#requestHeaders"/>
<int-http:header name="matrixVariables" expression="#matrixVariables"/>
<int-http:header name="cookies" expression="#cookies"/>
requestAttributes
是RequestAttributes
的实现。标准的是ServletRequestAttributes
,您可以在其中找到getRequest()
方法。是的,也可以在表达式中使用它:
<int-http:header name="request" expression="#requestAttributes.request"/>
另一方面,您始终可以在自己的代码中使用RequestContextHolder.currentRequestAttributes()
,因为它与ThreadLocal
绑定。
Spring MVC对Spring Integration一无所知,因此没有任何Message
处理。
无论如何你也可以这样走。为此,您应该引入@MessagingGateway
并从@Controller
。