自定义 Spring 集成 Web 服务 SOAP Envelope/Header

Customizing Spring Integration Web Service SOAP Envelope/Header

我正在尝试使用 Spring 集成来发送 SOAP 请求,例如

<int:chain input-channel="wsOutChannel" output-channel="stdoutChannel">
    <int-ws:header-enricher>
        <int-ws:soap-action value="..."/>
    </int-ws:header-enricher>
    <int-ws:outbound-gateway
            uri="..."/>
</int:chain>

但您只能添加 SOAP body,并且 Spring 集成会添加信封、header 和 body 标签,如

<SOAP-ENV:Envelope>
    <SOAP-ENV:Header>
        <SOAP-ENV:Body>
            ...
        </SOAP-ENV:Body>
    <SOAP-ENV:Header>
</SOAP-ENV:Envelope>

我需要自定义信封和header标签的特定属性,例如:

<soapenv:Envelope attribute1="value1" attribute2="value2">

和child个元素,例如:

<soapenv:Header>
    <child>...<child>
<soapenv:Header>

使用 Spring 集成 Web 服务是否可行,还是我不应该使用 int-ws:outbound-gateway 并采用不同的方法?

您可以添加一个 ClientInterceptor(通过 interceptor 属性),这样您就可以在发送请求之前对其进行修改。

编辑

@Artem 的建议更简单,但拦截器也可以让您访问响应;但无论哪种方式,代码都是相似的。

对于拦截器:

public class MyInterceptor extends ClientInterceptorAdapter {

    @Override
    public boolean handleRequest(MessageContext messageContext) throws WebServiceClientException {
        SoapMessage request = (SoapMessage) messageContext.getRequest();
        SoapEnvelope envelope = request.getEnvelope();
        envelope.addAttribute(new QName("foo"), "bar");
        SoapHeader header = envelope.getHeader();
        header.addHeaderElement(new QName("http://fiz/buz", "baz"));
        return super.handleRequest(messageContext);
    }

}

回调版本:

@Override
public void doWithMessage(WebServiceMessage message) throws IOException, TransformerException {
    SoapEnvelope envelope = ((SoapMessage) message).getEnvelope();
    envelope.addAttribute(new QName("foo"), "bar");
    SoapHeader header = envelope.getHeader();
    header.addHeaderElement(new QName("http://fiz/buz", "baz"));
}

我觉得你可以注射 WebServiceMessageCallback:

<xsd:attribute name="request-callback" type="xsd:string">
            <xsd:annotation>
                <xsd:documentation>
Reference to a Spring Web Services WebServiceMessageCallback. This enables changing
the Web Service request message after the payload has been written to it but prior
to invocation of the actual Web Service.
                </xsd:documentation>
                <xsd:appinfo>
                    <tool:annotation kind="ref">
                        <tool:expected-type type="org.springframework.ws.client.core.WebServiceMessageCallback"/>
                    </tool:annotation>
                </xsd:appinfo>
            </xsd:annotation>
        </xsd:attribute>

并将消息投射到 SoapMessage 并使用其 getEnvelope() 自定义所需的方式。