Done?
This commit is contained in:
@@ -76,7 +76,7 @@
|
||||
<para>
|
||||
The <interfacename>SoapMessage</interfacename> is an extension of
|
||||
<interfacename>WebServiceMessage</interfacename>. It contains SOAP-specific methods, such as getting
|
||||
SOAP Headers, SOAP Faults, etc. Generally, your code should only not be dependent on
|
||||
SOAP Headers, SOAP Faults, etc. Generally, your code should not be dependent on
|
||||
<interfacename>SoapMessage</interfacename>, because the content of the SOAP Body can be obtained via
|
||||
<methodname>getPayloadSource()</methodname> and <methodname>getPayloadResult()</methodname> in the
|
||||
<interfacename>WebServiceMessage</interfacename>. Only when it is necessary to perform SOAP-specific
|
||||
@@ -157,15 +157,6 @@
|
||||
</section>
|
||||
<section id="xpath">
|
||||
<title>Handling XML With XPath</title>
|
||||
<sidebar>
|
||||
<title>What is XPath?</title>
|
||||
<para>
|
||||
XPath is a language for addressing parts of an XML document.
|
||||
For more information about XPath, refer to the
|
||||
<ulink url="http://www.w3.org/TR/xpath">XPath specification</ulink>, or read the
|
||||
<ulink url="http://www.w3schools.com/xpath/">XPath tutorial</ulink>
|
||||
</para>
|
||||
</sidebar>
|
||||
<para>
|
||||
One of the best ways to handle XML is to use XPath. Quoting <xref linkend="effective-xml"/>, item 35:
|
||||
</para>
|
||||
|
||||
@@ -53,7 +53,7 @@
|
||||
</note>
|
||||
</section>
|
||||
<section id="security-xws-security-interceptor">
|
||||
<title>XwsSecurityInterceptor</title>
|
||||
<title><classname>XwsSecurityInterceptor</classname></title>
|
||||
<para>
|
||||
The
|
||||
<classname>XwsSecurityInterceptor</classname>
|
||||
|
||||
@@ -61,7 +61,7 @@
|
||||
<listitem>
|
||||
<para>
|
||||
An appropriate endpoint is searched for. If an endpoint is found, the invocation chain associated
|
||||
with the handler (preprocessors, postprocessors, and endpoints) will be executed in order to create
|
||||
with the endpoint (preprocessors, postprocessors, and endpoints) will be executed in order to create
|
||||
a response.
|
||||
</para>
|
||||
</listitem>
|
||||
@@ -328,7 +328,7 @@ public class MarshallingOrderEndpoint extends AbstractMarshallingPayloadEndpoint
|
||||
returned. The returned object is marshalled into XML, and used as the payload of the response message.
|
||||
The SOAP request handled by this endpoint will look like:
|
||||
</para>
|
||||
<programlisting><![CDATA[<SOAP-ENV:Envelope xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/">
|
||||
<programlisting id="server-order-request"><![CDATA[<SOAP-ENV:Envelope xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/">
|
||||
<SOAP-ENV:Body>
|
||||
<orderRequest xmlns="http://samples" id="42"/>
|
||||
</SOAP-ENV:Body>
|
||||
@@ -357,7 +357,7 @@ public class MarshallingOrderEndpoint extends AbstractMarshallingPayloadEndpoint
|
||||
<literal>marshaller</literal> bean.
|
||||
</para>
|
||||
</section>
|
||||
<section>
|
||||
<section id="server-at-endpoint">
|
||||
<title><interfacename>@Endpoint</interfacename></title>
|
||||
<para>
|
||||
The previous two programming models were based on inheritance, and handled individual XML mesages.
|
||||
@@ -427,14 +427,16 @@ public class AnnotationOrderEndpoint {
|
||||
<classname>PayloadRootAnnotationMethodEndpointMapping</classname> is the mapping that detects and
|
||||
handles the <interfacename>@PayloadRoot</interfacename> annotations.
|
||||
</para>
|
||||
<para>
|
||||
As an alternative to using marshalling, we could have used <link linkend="xpath">XPath</link> to
|
||||
extract the information out of the incoming XML request. Spring-WS offers another annotation for
|
||||
this purpose: <interfacename>@XPathParam</interfacename>. You simply annotate a method paramters
|
||||
with this annotation, and it will be bound with the evaluation of that annotation.
|
||||
Here is an example:
|
||||
</para>
|
||||
<programlisting><![CDATA[package samples;
|
||||
<section>
|
||||
<title><interfacename>@XPathParam</interfacename></title>
|
||||
<para>
|
||||
As an alternative to using marshalling, we could have used <link linkend="xpath">XPath</link> to
|
||||
extract the information out of the incoming XML request. Spring-WS offers another annotation for
|
||||
this purpose: <interfacename>@XPathParam</interfacename>. You simply annotate a method paramters
|
||||
with this annotation, and it will be bound with the evaluation of that annotation.
|
||||
Here is an example:
|
||||
</para>
|
||||
<programlisting id="server-payload-root-annotation"><![CDATA[package samples;
|
||||
|
||||
import javax.xml.transform.Source;
|
||||
|
||||
@@ -457,7 +459,12 @@ public class AnnotationOrderEndpoint {
|
||||
}
|
||||
|
||||
}]]></programlisting>
|
||||
<programlisting><![CDATA[<beans>
|
||||
<para>
|
||||
Since we use the prefix <literal>s</literal> in our XPath expression, we must bind it to the
|
||||
<uri>http://samples</uri> namespace:
|
||||
</para>
|
||||
|
||||
<programlisting><![CDATA[<beans>
|
||||
<bean id="orderEndpoint" class="samples.AnnotationOrderEndpoint">
|
||||
<constructor-arg ref="orderService"/>
|
||||
</bean>
|
||||
@@ -466,81 +473,282 @@ public class AnnotationOrderEndpoint {
|
||||
|
||||
<bean class="org.springframework.ws.server.endpoint.mapping.PayloadRootAnnotationMethodEndpointMapping"/>
|
||||
|
||||
<bean class="org.springframework.ws.server.endpoint.adapter.XPathParamAnnotationMethodEndpointAdapter" />
|
||||
]]><emphasis role="bold"><![CDATA[<bean class="org.springframework.ws.server.endpoint.adapter.XPathParamAnnotationMethodEndpointAdapter">
|
||||
<property name="namespaces">
|
||||
<props>
|
||||
<prop key="s">http://samples</prop>
|
||||
</props>
|
||||
</property>
|
||||
</bean>]]></emphasis><![CDATA[
|
||||
|
||||
</beans>]]></programlisting>
|
||||
<para>
|
||||
Using the <interfacename>@XPathParam</interfacename>, you can bind to all the data types supported by
|
||||
XPath:
|
||||
<itemizedlist>
|
||||
<listitem><para><type>boolean</type> or <classname>Boolean</classname></para></listitem>
|
||||
<listitem><para><type>double</type> or <classname>Double</classname></para></listitem>
|
||||
<listitem><para><classname>String</classname></para></listitem>
|
||||
<listitem><para><interfacename>Node</interfacename></para></listitem>
|
||||
<listitem><para><interfacename>NodeList</interfacename></para></listitem>
|
||||
</itemizedlist>
|
||||
</para>
|
||||
<para>
|
||||
Using the <interfacename>@XPathParam</interfacename>, you can bind to all the data types supported by
|
||||
XPath:
|
||||
<itemizedlist>
|
||||
<listitem><para><type>boolean</type> or <classname>Boolean</classname></para></listitem>
|
||||
<listitem><para><type>double</type> or <classname>Double</classname></para></listitem>
|
||||
<listitem><para><classname>String</classname></para></listitem>
|
||||
<listitem><para><interfacename>Node</interfacename></para></listitem>
|
||||
<listitem><para><interfacename>NodeList</interfacename></para></listitem>
|
||||
</itemizedlist>
|
||||
</para>
|
||||
</section>
|
||||
</section>
|
||||
</section>
|
||||
<section id="server-endpoint-mapping">
|
||||
<title>Endpoint mappings</title>
|
||||
<para>
|
||||
The endpoint mapping is responsible for mapping incoming messages to appropriate endpoints. It does this by
|
||||
delivering a <classname>EndpointInterceptorChain</classname>, which consists of the endpoint that matches
|
||||
the incoming request, and an optional list of endpoint interceptors. When a message is received by the
|
||||
<classname>MessageDispatcher</classname>, it will ask the registered endpoint mappings to come up with a
|
||||
appropriate <classname>HandlerExecutionChain</classname>. After that, the
|
||||
<classname>MessageDispatcher</classname> will invoke the endpoint and interceptors in the chain.
|
||||
The endpoint mapping is responsible for mapping incoming messages to appropriate endpoints. There are some
|
||||
endpoint mappings you can use out of the box, for example, the
|
||||
<classname>PayloadRootQNameEndpointMapping</classname> or the
|
||||
<classname>SoapActionEndpointMapping</classname>, but let's first examine the general concept of a
|
||||
<interfacename>EndpointMapping</interfacename>.
|
||||
</para>
|
||||
<para>
|
||||
Most endpoint mappings inherit from the <classname>AbstractEndpointMapping</classname>, which offers the
|
||||
following properties:
|
||||
<informaltable>
|
||||
<tgroup cols="2">
|
||||
<tbody>
|
||||
<row>
|
||||
<entry>
|
||||
<methodname>interceptors</methodname>
|
||||
</entry>
|
||||
<entry>
|
||||
the list of interceptors use. <interfacename>EndpointInterceptor</interfacename>s are
|
||||
discussed in <xref linkend="ws-endpoint-interceptor"/>.
|
||||
</entry>
|
||||
</row>
|
||||
<row>
|
||||
<entry>
|
||||
<methodname>defaultHandler</methodname>
|
||||
</entry>
|
||||
<entry>
|
||||
the default handler to use. This endpoint will be returned if no specific mapping was
|
||||
found.
|
||||
</entry>
|
||||
</row>
|
||||
<row>
|
||||
<entry>
|
||||
|
||||
</entry>
|
||||
</row>
|
||||
|
||||
</tbody>
|
||||
</tgroup>
|
||||
</informaltable>
|
||||
A <interfacename>EndpointMapping</interfacename> delivers a <classname>EndpointInvocationChain</classname>,
|
||||
which contains the endpoint that matches the incoming request, and may also contain a list of endpoint
|
||||
interceptors that are applied to the request and response. When a request comes in, the
|
||||
<classname>MessageDispatcher</classname> will hand it over to the endpoint mapping to let it inspect the
|
||||
request and come up with an appropriate <classname>EndpointInvocationChain</classname>. Then
|
||||
the <classname>MessageDispatcher</classname> will invoce the endpoint and any interceptors in the chain.
|
||||
</para>
|
||||
<para>
|
||||
The concept of configurable endpoint mappings that can optionally contain interceptors (which can manipulate
|
||||
the request or the response, or both) is extremely powerful. A lot of supporting functionality can be built
|
||||
into custom <interfacename>EndpointMapping</interfacename>s. Think of a custom endpoint mapping that
|
||||
chooses an endpoint not only based on the contents of a message, but also a specific SOAP headers.
|
||||
</para>
|
||||
<para>
|
||||
Most endpoint mappings inherit from the <classname>AbstractEndpointMapping</classname>, which offers a
|
||||
<property>interceptors</property> property, which is the list of interceptors to use.
|
||||
<interfacename>EndpointInterceptor</interfacename>s are discussed in
|
||||
<xref linkend="server-endpoint-interceptor"/>. Additionally, there is the
|
||||
<property>defaultEndpoint</property>, which is the default endpoint to use, when this endpoint mapping does
|
||||
not result in a matching endpoint.
|
||||
</para>
|
||||
<section>
|
||||
<title>SoapActionEndpointMapping</title>
|
||||
<para/>
|
||||
<title><classname>PayloadRootQNameEndpointMapping</classname></title>
|
||||
<para>
|
||||
The <classname>PayloadRootQNameEndpointMapping</classname> will use the qualified name of the root
|
||||
element of the request payload to determine the endpoint that handles it. A qualified name consists of
|
||||
a <emphasis>namespace URI</emphasis> and a <emphasis>local part</emphasis>, the combination of which
|
||||
should be unique within the mapping. Here is an example:
|
||||
</para>
|
||||
<programlisting><![CDATA[<beans>
|
||||
|
||||
]]><lineannotation><!-- no <literal>'id'</literal> required, <interfacename>EndpointMapping</interfacename> beans are automatically detected by the <classname>MessageDispatcher</classname> --></lineannotation><![CDATA[
|
||||
<bean id="endpointMapping" class="org.springframework.ws.server.endpoint.mapping.PayloadRootQNameEndpointMapping">
|
||||
<property name="mappings">
|
||||
<props>
|
||||
<prop key="{http://samples}orderRequest">getOrderEndpoint</prop>
|
||||
<prop key="{http://samples}order">createOrderEndpoint</prop>
|
||||
</props>
|
||||
</property>
|
||||
</bean>
|
||||
|
||||
<bean id="getOrderEndpoint" class="samples.GetOrderEndpoint">
|
||||
<constructor-arg ref="orderService"/>
|
||||
</bean>
|
||||
|
||||
<bean id="createOrderEndpoint" class="samples.CreateOrderEndpoint">
|
||||
<constructor-arg ref="orderService"/>
|
||||
</bean>
|
||||
<beans>]]></programlisting>
|
||||
<para>
|
||||
The qualified name is expressed as <literal>{</literal> + namespace URI + <literal>}</literal> +
|
||||
local part. Thus, the endpoint mapping above routes requests for which have a payload root element with
|
||||
namespace <uri>http://samples</uri> and local part <literal>orderRequest</literal> to the
|
||||
<literal>'getOrderEndpoint'</literal>. Requests with a local part <literal>order</literal> will
|
||||
be routed to the <literal>'createController'</literal>. As a result of this mapping, the SOAP message
|
||||
shown <link linkend="server-order-request">above</link> will be mapped to the
|
||||
<literal>getOrderEndpoint</literal>.
|
||||
</para>
|
||||
</section>
|
||||
<section>
|
||||
<title>PayloadRootQNameEndpointMapping</title>
|
||||
<para/>
|
||||
<title><classname>SoapActionEndpointMapping</classname></title>
|
||||
<para>
|
||||
Rather than base the routing on the contents of the message with the
|
||||
<classname>PayloadRootQNameEndpointMapping</classname>, you can use the <literal>SOAPAction</literal>
|
||||
HTTP header to route messages. Every client sends this header when making a SOAP request, and the
|
||||
header value used for a request is defined in the WSDL. By making the <literal>SOAPAction</literal>
|
||||
unique per operation, you can use it a a discriminator. Here is an example:
|
||||
</para>
|
||||
<programlisting><![CDATA[<beans>
|
||||
<bean id="endpointMapping" class="org.springframework.ws.soap.server.endpoint.mapping.SoapActionEndpointMapping">
|
||||
<property name="mappings">
|
||||
<props>
|
||||
<prop key="http://samples/RequestOrder">getOrderEndpoint</prop>
|
||||
<prop key="http://samples/CreateOrder">createOrderEndpoint</prop>
|
||||
</props>
|
||||
</property>
|
||||
</bean>
|
||||
|
||||
<bean id="getOrderEndpoint" class="samples.GetOrderEndpoint">
|
||||
<constructor-arg ref="orderService"/>
|
||||
</bean>
|
||||
|
||||
<bean id="createOrderEndpoint" class="samples.CreateOrderEndpoint">
|
||||
<constructor-arg ref="orderService"/>
|
||||
</bean>
|
||||
</beans>]]></programlisting>
|
||||
<para>
|
||||
The mapping above routes requests which have the a <literal>SOAPAction</literal> of
|
||||
<uri>http://samples/RequestOrder</uri> to the <literal>'getOrderEndpoint'</literal>. Requests with
|
||||
<uri>http://samples/CreateOrder</uri> will be routed to the <literal>'createController'</literal>.
|
||||
Note that using SOAP Action headers is SOAP-specific, so it cannot be used when using Plain Old XML.
|
||||
</para>
|
||||
</section>
|
||||
<section id="server-method-endpoint-mapping">
|
||||
<title><classname>MethodEndpointMapping</classname></title>
|
||||
<para/>
|
||||
<para>
|
||||
As explain in <xref linkend="server-at-endpoint"/>, the <interfacename>@Endpoint</interfacename> model
|
||||
allows you to handle multiple requests in one endpoint class. This is the responsibility of the
|
||||
<classname>MethodEndpointMapping</classname>. Similar to the endpoint mapping described above, the
|
||||
mapping determines which method is to be invoked for an incoming request message.
|
||||
</para>
|
||||
<para>
|
||||
There are two endpoint mappings that can direct requests to methods: the
|
||||
<classname>PayloadRootAnnotationMethodEndpointMapping</classname> and the
|
||||
<classname>SoapActionAnnotationMethodEndpointMapping</classname>, both of which are very similar to
|
||||
their non-method counterparts described above.
|
||||
</para>
|
||||
<para>
|
||||
The <classname>PayloadRootAnnotationMethodEndpointMapping</classname> uses the
|
||||
<interfacename>@PayloadRoot</interfacename> annotation, with the <literal>localPart</literal> and
|
||||
<literal>namespace</literal> elements, to mark methods with a particular qualified
|
||||
name. Whenever a message comes in which has this qualified name for the payload root element, the
|
||||
method will be invoked. For an example, see <link linkend="server-payload-root-annotation">above</link>.
|
||||
</para>
|
||||
<para>
|
||||
Alternatively, the <classname>SoapActionAnnotationMethodEndpointMapping</classname> uses the
|
||||
<interfacename>@SoapAction</interfacename> annotation to mark methods with a particular SOAP Action.
|
||||
Whenever a message comes in which has this <literal>SOAPAction</literal> header, the
|
||||
method will be invoked.
|
||||
</para>
|
||||
</section>
|
||||
<section id="server-endpoint-interceptor">
|
||||
<title>Adding <interfacename>EndpointInterceptors</interfacename></title>
|
||||
<para/>
|
||||
<title>Intecepting requests - the <interfacename>EndpointInterceptor</interfacename> interface</title>
|
||||
<para>
|
||||
The endpoint mapping mechanism has the notion of endpoint interceptors, that can be extremely useful
|
||||
when you want to apply specific functionality to certain requests, for example, dealing with
|
||||
security-related SOAP headers, or logging the request and response message.
|
||||
</para>
|
||||
<para>
|
||||
Interceptors located in the endpoint mapping must implement
|
||||
<interfacename>EndpointInterceptor</interfacename> from the
|
||||
<package>org.springframework.ws.server</package> package. This interface defines three methods, one that
|
||||
can be used for handling the request message has been determined, <emphasis>before</emphasis> the actual
|
||||
endpoint will be executed, one that can be used for handling a normal response message, and one that
|
||||
can be used for handling fault messages, both of which will be called <emphasis>after</emphasis> the
|
||||
endpoint is executed. These three methods should provide enough flexibility to do all kinds of
|
||||
pre- and post-processing.
|
||||
</para>
|
||||
<para>
|
||||
The <methodname>handleRequest(..)</methodname> methods on the interceptor returns a boolean value. You
|
||||
can use this method to break or continue the processing of the invocation chain. When this method
|
||||
returns <literal>true</literal>, the endpoint execution chain will continue, when it returns
|
||||
<literal>false</literal>, the <classname>MessageDispatcher</classname> assumes the interceptor itself
|
||||
has taken care of things and does not continue executing the other interceptors and the actual endoint
|
||||
in the invocation chain. The <methodname>handleResponse(..)</methodname> and
|
||||
<methodname>handleFault(..)</methodname> methods also have a boolean return value. When these methods
|
||||
return <literal>false</literal>, the response will not be sent back to the client.
|
||||
</para>
|
||||
<para>
|
||||
There are a number of standard <interfacename>EndpointInterceptor</interfacename> implementations you
|
||||
can use in your Web service. Additionally, there is the <classname>XwsSecurityInterceptor</classname>,
|
||||
which is described in <xref linkend="security-xws-security-interceptor"/>.
|
||||
</para>
|
||||
<section>
|
||||
<title><classname>PayloadLoggingInterceptor</classname> and
|
||||
<classname>SoapEnvelopeLoggingInterceptor</classname></title>
|
||||
<para>
|
||||
When developing a Web service, it can be useful to log the incoming and outgoing XML messages to
|
||||
the log. Spring Web Services facilitates this with the
|
||||
<classname>PayloadLoggingInterceptor</classname> and the
|
||||
<classname>SoapEnvelopeLoggingInterceptor</classname>. The former just logs the payload of the
|
||||
message to the Commons Logging Log; the latter logs the entire SOAP Envelope, including SOAP
|
||||
headers. This example shows you how to define them in an endpoint mapping:
|
||||
</para>
|
||||
<programlisting><![CDATA[<beans>
|
||||
<bean id="endpointMapping"
|
||||
class="org.springframework.ws.server.endpoint.mapping.PayloadRootQNameEndpointMapping">
|
||||
<property name="interceptors">
|
||||
<list>
|
||||
<ref bean="loggingInterceptor"/>
|
||||
</list>
|
||||
</property>
|
||||
<property name="mappings">
|
||||
<props>
|
||||
<prop key="{http://samples}orderRequest">getOrderEndpoint</prop>
|
||||
<prop key="{http://samples}order">createOrderEndpoint</prop>
|
||||
</props>
|
||||
</property>
|
||||
</bean>
|
||||
|
||||
<bean id="loggingInterceptor"
|
||||
class="org.springframework.ws.server.endpoint.interceptor.PayloadLoggingInterceptor"/>
|
||||
</beans>]]></programlisting>
|
||||
<para>
|
||||
Both of these interceptors have two properties: <property>logRequest</property> and
|
||||
<property>logResponse</property>, which can be set to <literal>false</literal> to disable logging
|
||||
for either request of response messages.
|
||||
</para>
|
||||
</section>
|
||||
<section>
|
||||
<title><classname>PayloadValidatingInterceptor</classname></title>
|
||||
<para>
|
||||
One of the benefits of using a contract-first development style is that we can use the schema to
|
||||
validate incoming and outgoing XML messages. Spring-WS facilitates this with the
|
||||
<classname>PayloadValidatingInterceptor</classname>. This interceptor requires a reference to one
|
||||
or more W3C XML or RELAX NG schemas, and can be set to validate requests or responses, or both.
|
||||
</para>
|
||||
<note>
|
||||
<para>
|
||||
Note that request validation may sound like a good idea, but makes the resulting Web service
|
||||
very strict. Usually, it is not really important whether the request validates, only if the
|
||||
endpoint can get sufficient information to fullfill a request. Validating the response
|
||||
<emphasis>is</emphasis> a good idea, because the endpoint should adhere to adhere to its schema.
|
||||
Remember Postel's Law:
|
||||
<quote>Be conservative in what you do; be liberal in what you accept from others.</quote>
|
||||
</para>
|
||||
</note>
|
||||
<para>
|
||||
Here is an example that uses the <classname>PayloadValidatingInterceptor</classname>:
|
||||
</para>
|
||||
<programlisting><![CDATA[<bean id="validatingInterceptor"
|
||||
class="org.springframework.ws.soap.server.endpoint.interceptor.PayloadValidatingInterceptor">
|
||||
<property name="schema" value="/WEB-INF/orders.xsd"/>
|
||||
<property name="validateRequest" value="false"/>
|
||||
<property name="validateResponse" value="true"/>
|
||||
</bean>]]></programlisting>
|
||||
<para>
|
||||
In this example, we use the schema in <filename>/WEB-INF/orders.xsd</filename> to validate the
|
||||
response, but not the request.
|
||||
</para>
|
||||
</section>
|
||||
<section>
|
||||
<title><classname>PayloadTransformingInterceptor</classname></title>
|
||||
<para>
|
||||
To transform the payload to another XML format, Spring Web Services offers the
|
||||
<classname>PayloadTransformingInterceptor</classname>. This endpoint interceptor is based on XSLT
|
||||
stylesheets, and is especially useful when supporting with multiple version of a Web service:
|
||||
you simply can transform the older message format to the new format.
|
||||
Here is an example to use the <classname>PayloadTransformingInterceptor</classname>:
|
||||
</para>
|
||||
<programlisting><![CDATA[<bean id="transformingInterceptor"
|
||||
class="org.springframework.ws.server.endpoint.interceptor.PayloadTransformingInterceptor">
|
||||
<property name="requestXslt" value="/WEB-INF/oldRequests.xslt"/>
|
||||
<property name="requestXslt" value="/WEB-INF/oldResponses.xslt"/>
|
||||
</bean>]]></programlisting>
|
||||
<para>
|
||||
We are simply transforming requests using <filename>/WEB-INF/oldRequests.xslt</filename>, and
|
||||
response messages using <filename>/WEB-INF/oldResponses.xslt</filename>. Note that, since
|
||||
endpoint interceptors are registered at the endpoint mapping level, you can simply create a
|
||||
endpoint mapping that applies to the "old style" messages, and add the interceptor to that mapping.
|
||||
Hence, the transformation will only apply to these "old style" message.
|
||||
</para>
|
||||
</section>
|
||||
</section>
|
||||
</section>
|
||||
<section id="server-endpoint-exception-resolver">
|
||||
|
||||
Reference in New Issue
Block a user