1

我正在使用 SimpleWebServiceInboundGateway,目前我有网关将请求放到一个通道上,然后从通道中消耗一个流。一切似乎都很好。

我的问题是,如果您有多个不同的肥皂端点服务,每个服务的操作略有不同,我如何将这些端点映射到不同的流,这样做的正确方法是什么?是否期望每个soap Web 服务端点都有一个新的SimpleWebServiceInboundGateway 并使用EndpointMapper 映射到每个端点?或者有更好的做法吗?我不太确定它是否应该有多个 Soap 网关。

此外,有什么简单的方法可以访问用于在流程中进行 ws 调用的 URI/URL?我注意到它似乎不在标题中。

这是我的示例配置:

/**
 * URL mappings used by WS endpoints
 */
public static final String[] WS_URL_MAPPINGS = {"/services/*", "*.wsdl", "*.xsd"};
public static final String GATEWAY_INBOUND_CHANNEL_NAME  = "wsGatewayInboundChannel";
public static final String GATEWAY_OUTBOUND_CHANNEL_NAME = "wsGatewayOutboundChannel";


/**
 * Register the servlet mapper, note that it uses MessageDispatcher
 */
@Bean
public ServletRegistrationBean messageDispatcherServlet(ApplicationContext applicationContext) {
    MessageDispatcherServlet servlet = new MessageDispatcherServlet();
    servlet.setApplicationContext(applicationContext);
    servlet.setTransformWsdlLocations(true);
    servlet.setTransformSchemaLocations(true);
    servlet.setPublishEvents(true);
    ServletRegistrationBean servletDef = new ServletRegistrationBean(servlet, WS_URL_MAPPINGS);
    servletDef.setLoadOnStartup(1);
    return servletDef;
}

/**
 * Create a new Direct channels to handle the messages
 */
@Bean
public MessageChannel wsGatewayInboundChannel() {
    return MessageChannels.direct(GATEWAY_INBOUND_CHANNEL_NAME).get();
}
@Bean
public MessageChannel wsGatewayOutboundChannel() {
    return MessageChannels.direct(GATEWAY_OUTBOUND_CHANNEL_NAME).get();
}

/**
 * Startup the WebServiceInboundGateway Endpoint, this will handle the incoming SOAP requests
 *  and place them onto the request channel
 */
@Bean
public SimpleWebServiceInboundGateway webServiceInboundGateway(
        @Value("${spring.ws.should.track:true}") boolean shouldTrack
) {
    SimpleWebServiceInboundGateway wsg = new SimpleWebServiceInboundGateway();
    wsg.setRequestChannel(wsGatewayInboundChannel());
    wsg.setReplyChannel(wsGatewayOutboundChannel());
    wsg.setExtractPayload(false);  // Send the full RAW SOAPMessage and not just payload
    wsg.setLoggingEnabled(true);
    wsg.setShouldTrack(shouldTrack);
    wsg.setCountsEnabled(true);
    return wsg;
}


/**
 * Map the allowable service Uri's.
 *
 * although this isn't needed (can map everything using the mapping.setDefaultEndpoint)
 *  using this approach ensures that people don't use unexpected uris, probably can
 *  find a better way to deal with this in the future
 */
@Bean
public EndpointMapping uriEndpointMapping(@Qualifier("serviceUris") List<String> serviceUris
        , PayloadValidatingInterceptor payloadValidatingInterceptor
        , SimpleWebServiceInboundGateway webServiceInboundGateway) {
    UriEndpointMapping mapping = new UriEndpointMapping();
    mapping.setUsePath(true);
    Map<String, Object> endpointMap = new HashMap<>();
    endpointMap.put("/services/myservice1", webServiceInboundGateway);

    mapping.setEndpointMap(endpointMap);
    //mapping.setDefaultEndpoint(webServiceInboundGateway());

    return mapping;
}


@Bean
public IntegrationFlow itemLookupFlow(ItemLookupRequestToItemDetailsRequestTransformer requestTransformer
        , ItemDetailsResponseToItemLookupResponseTransformer responseTransformer) {
    return IntegrationFlows.from("wsGatewayInboundChannel")
            .transform(new MyTransformer())
            .log(LoggingHandler.Level.INFO)
            .handle(myBean, "execute")
            .get();
}
4

1 回答 1

4

或者有更好的做法吗?

为什么每个人都将 Spring Integration 视为不好的做法?想象一下您在应用程序中不使用 Spring Integration 而只使用 Spring WS 的情况。所以,现在你需要编写几个端点。你做什么?@Endpoint正确,使用和/或适当的 url 映射开发几个类。不知何故,您并没有说这是不好的做法,只是遵循框架要求。

那么,为什么您认为 distinct SimpleWebServiceInboundGateways 是不好的方式呢?

我认为不同的端点确实意味着完全不相关的逻辑、不同的转换、路由以及最终的 SOAP 解组。

因此,将一个新SimpleWebServiceInboundGateway的及其下游流视为一个单独的 Spring WS@Endpoint类。

要获取 URL,您应该注入自定义SoapHeaderMapper. 我认为SoapMessage有一些钩子可以提取该信息。

于 2017-11-25T13:58:36.987 回答