cxf-commits mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From conflue...@apache.org
Subject [CONF] Apache CXF Documentation > Interceptors
Date Thu, 02 Feb 2012 17:21:00 GMT
<html>
<head>
    <base href="https://cwiki.apache.org/confluence">
            <link rel="stylesheet" href="/confluence/s/2042/9/1/_/styles/combined.css?spaceKey=CXF20DOC&amp;forWysiwyg=true"
type="text/css">
    </head>
<body style="background: white;" bgcolor="white" class="email-body">
<div id="pageContent">
<div id="notificationFormat">
<div class="wiki-content">
<div class="email">
    <h2><a href="https://cwiki.apache.org/confluence/display/CXF20DOC/Interceptors">Interceptors</a></h2>
    <h4>Page <b>edited</b> by             <a href="https://cwiki.apache.org/confluence/display/~coheigea@apache.org">Colm
O hEigeartaigh</a>
    </h4>
        <br/>
                         <h4>Changes (1)</h4>
                                 
    
<div id="page-diffs">
                    <table class="diff" cellpadding="0" cellspacing="0">
    
            <tr><td class="diff-snipped" >...<br></td></tr>
            <tr><td class="diff-unchanged" > <br>Client cxfClient = ClientProxy.getClient(client);
<br></td></tr>
            <tr><td class="diff-changed-lines" ><span class="diff-changed-words">cxfClient.getInInterceptor<span
class="diff-added-chars"style="background-color: #dfd;">s</span>().add(myInterceptor);</span>
<br></td></tr>
            <tr><td class="diff-unchanged" > <br>// then you can call the
service <br></td></tr>
            <tr><td class="diff-snipped" >...<br></td></tr>
    
            </table>
    </div>                            <h4>Full Content</h4>
                    <div class="notificationGreySide">
        <h1><a name="Interceptors-InterceptorsandPhases"></a>Interceptors
and Phases</h1>

<p>Interceptors are the fundamental processing unit inside CXF. When a service is invoked,
an InterceptorChain is created and invoked. Each interceptor gets a chance to do what they
want with the message. This can include reading it, transforming it, processing headers, validating
the message, etc.</p>

<p>Interceptors are used with both CXF clients and CXF servers.  When a CXF client invokes
a CXF server, there is an outgoing interceptor chain for the client and an incoming chain
for the server.  When the server sends the response back to the client, there is an outgoing
chain for the server and an incoming one for the client.  Additionally, in the case of <a
href="http://java.sun.com/j2ee/1.4/docs/api/javax/xml/soap/SOAPFault.html" class="external-link"
rel="nofollow">SOAPFaults</a>, a CXF web service will create a separate outbound
error handling chain and the client will create an inbound error handling chain.</p>

<p>Some examples of interceptors inside CXF include:</p>
<ul>
	<li>SoapActionInterceptor - Processes the SOAPAction header and selects an operation
if it's set.</li>
	<li>StaxInInterceptor - Creates a Stax XMLStreamReader from the transport input stream.</li>
	<li>Attachment(In/Out)Interceptor - Turns a multipart/related message into a series
of attachments.</li>
</ul>


<p>InterceptorChains are divided up into Phases. The phase that each interceptor runs
in is declared in the interceptor's constructor.  Each phase may contain many interceptors.
On the incoming chains, you'll have the following phases:</p>
<div class='table-wrap'>
<table class='confluenceTable'><tbody>
<tr>
<th class='confluenceTh'> Phase </th>
<th class='confluenceTh'> Functions </th>
</tr>
<tr>
<td class='confluenceTd'> RECEIVE </td>
<td class='confluenceTd'> Transport level processing </td>
</tr>
<tr>
<td class='confluenceTd'> (PRE/USER/POST)_STREAM </td>
<td class='confluenceTd'> Stream level processing/transformations </td>
</tr>
<tr>
<td class='confluenceTd'> READ </td>
<td class='confluenceTd'> This is where header reading typically occurs. </td>
</tr>
<tr>
<td class='confluenceTd'> (PRE/USER/POST)_PROTOCOL </td>
<td class='confluenceTd'> Protocol processing, such as JAX-WS SOAP handlers </td>
</tr>
<tr>
<td class='confluenceTd'> UNMARSHAL </td>
<td class='confluenceTd'> Unmarshalling of the request </td>
</tr>
<tr>
<td class='confluenceTd'> (PRE/USER/POST)_LOGICAL </td>
<td class='confluenceTd'> Processing of the umarshalled request </td>
</tr>
<tr>
<td class='confluenceTd'> PRE_INVOKE </td>
<td class='confluenceTd'> Pre invocation actions </td>
</tr>
<tr>
<td class='confluenceTd'> INVOKE </td>
<td class='confluenceTd'> Invocation of the service </td>
</tr>
<tr>
<td class='confluenceTd'> POST_INVOKE </td>
<td class='confluenceTd'> Invocation of the outgoing chain if there is one </td>
</tr>
</tbody></table>
</div>

<p>On the outgoing chain there are the following phases:</p>
<div class='table-wrap'>
<table class='confluenceTable'><tbody>
<tr>
<th class='confluenceTh'> Phase </th>
<th class='confluenceTh'> Functions </th>
</tr>
<tr>
<td class='confluenceTd'> SETUP </td>
<td class='confluenceTd'> Any set up for the following phases </td>
</tr>
<tr>
<td class='confluenceTd'> (PRE/USER/POST)_LOGICAL </td>
<td class='confluenceTd'> Processing of objects about to marshalled </td>
</tr>
<tr>
<td class='confluenceTd'> PREPARE_SEND </td>
<td class='confluenceTd'> Opening of the connection </td>
</tr>
<tr>
<td class='confluenceTd'> PRE_STREAM </td>
<td class='confluenceTd'>&nbsp;</td>
</tr>
<tr>
<td class='confluenceTd'> PRE_PROTOCOL </td>
<td class='confluenceTd'> Misc protocol actions. </td>
</tr>
<tr>
<td class='confluenceTd'> WRITE </td>
<td class='confluenceTd'> Writing of the protocol message, such as the SOAP Envelope.
</td>
</tr>
<tr>
<td class='confluenceTd'> MARSHAL </td>
<td class='confluenceTd'> Marshalling of the objects </td>
</tr>
<tr>
<td class='confluenceTd'> (USER/POST)_PROTOCOL </td>
<td class='confluenceTd'> Processing of the protocol message. </td>
</tr>
<tr>
<td class='confluenceTd'> (USER/POST)_STREAM </td>
<td class='confluenceTd'> Processing of the byte level message </td>
</tr>
<tr>
<td class='confluenceTd'> SEND </td>
<td class='confluenceTd'>&nbsp;</td>
</tr>
</tbody></table>
</div>


<p>After the SEND phase, there are a bunch of "*_ENDING" phases that are symmetrical
to the above phases to allow the interceptors to cleanup and close anything that they had
opened or started in the above phases:</p>

<div class='table-wrap'>
<table class='confluenceTable'><tbody>
<tr>
<th class='confluenceTh'> Phase </th>
<th class='confluenceTh'> Functions </th>
</tr>
<tr>
<td class='confluenceTd'> SEND_ENDING </td>
<td class='confluenceTd'>&nbsp;</td>
</tr>
<tr>
<td class='confluenceTd'> POST_STREAM_ENDING </td>
<td class='confluenceTd'>&nbsp;</td>
</tr>
<tr>
<td class='confluenceTd'> USER_STREAM_ENDING </td>
<td class='confluenceTd'>&nbsp;</td>
</tr>
<tr>
<td class='confluenceTd'> POST_PROTOCOL_ENDING </td>
<td class='confluenceTd'>&nbsp;</td>
</tr>
<tr>
<td class='confluenceTd'> USER_PROTOCOL_ENDING </td>
<td class='confluenceTd'>&nbsp;</td>
</tr>
<tr>
<td class='confluenceTd'> MARSHAL_ENDING </td>
<td class='confluenceTd'>&nbsp;</td>
</tr>
<tr>
<td class='confluenceTd'> WRITE_ENDING </td>
<td class='confluenceTd'>&nbsp;</td>
</tr>
<tr>
<td class='confluenceTd'> PRE_PROTOCOL_ENDING </td>
<td class='confluenceTd'>&nbsp;</td>
</tr>
<tr>
<td class='confluenceTd'> PRE_STREAM_ENDING </td>
<td class='confluenceTd'>&nbsp;</td>
</tr>
<tr>
<td class='confluenceTd'> PREPARE_SEND_ENDING </td>
<td class='confluenceTd'>&nbsp;</td>
</tr>
<tr>
<td class='confluenceTd'> POST_LOGICAL_ENDING </td>
<td class='confluenceTd'>&nbsp;</td>
</tr>
<tr>
<td class='confluenceTd'> USER_LOGICAL_ENDING </td>
<td class='confluenceTd'>&nbsp;</td>
</tr>
<tr>
<td class='confluenceTd'> PRE_LOGICAL_ENDING </td>
<td class='confluenceTd'>&nbsp;</td>
</tr>
<tr>
<td class='confluenceTd'> SETUP_ENDING </td>
<td class='confluenceTd'> Usually results in all the streams being closed and the final
data being sent on the wire. </td>
</tr>
</tbody></table>
</div>



<h1><a name="Interceptors-InterceptorProviders"></a>InterceptorProviders</h1>

<p>Several different components inside CXF may provide interceptors to an InterceptorChain.
These implement the InterceptorProvider interface:</p>
<div class="code panel" style="border-width: 1px;"><div class="codeContent panelContent">
<pre class="code-java">
<span class="code-keyword">public</span> <span class="code-keyword">interface</span>
InterceptorProvider {

    List&lt;Interceptor&gt; getInInterceptors();

    List&lt;Interceptor&gt; getOutInterceptors();

    List&lt;Interceptor&gt; getOutFaultInterceptors();

    List&lt;Interceptor&gt; getInFaultInterceptors();
}
</pre>
</div></div>
<p>To add an interceptor to an interceptor chain, you'll want to add it to one of the
Interceptor Providers.</p>
<div class="code panel" style="border-width: 1px;"><div class="codeContent panelContent">
<pre class="code-java">
MyInterceptor interceptor = <span class="code-keyword">new</span> MyInterceptor();
provider.getInInterceptors().add(interceptor);
</pre>
</div></div>
<p>Some InterceptorProviders inside CXF are:</p>
<ul>
	<li>Client</li>
	<li>Endpoint</li>
	<li>Service</li>
	<li>Bus</li>
	<li>Binding</li>
</ul>


<h1><a name="Interceptors-WritingandconfiguringanInterceptor"></a>Writing
and configuring an Interceptor</h1>

<p>The CXF distribution is shipped with a demo called <a href="http://svn.apache.org/viewvc/cxf/trunk/distribution/src/main/release/samples/configuration_interceptor/"
class="external-link" rel="nofollow">configuration_interceptor </a> which shows how
to develop a user interceptor and configure the interceptor into its interceptor chain.</p>


<h2><a name="Interceptors-WritinganInterceptor"></a>Writing an Interceptor</h2>

<p>Writing an interceptor is relatively simple. Your interceptor needs to extend from
either the AbstractPhaseInterceptor or one of its <a href="http://tinyurl.com/3bkho8" class="external-link"
rel="nofollow">many subclasses</a> such as AbstractSoapInterceptor. Extending from
AbstractPhaseInterceptor allows your interceptor to access the methods of the <a href="http://tinyurl.com/24gj28"
class="external-link" rel="nofollow">Message</a> interface. For example, AttachmentInInterceptor
is used in CXF to turn a multipart/related message into a series of attachments. It looks
like below:</p>
<div class="code panel" style="border-width: 1px;"><div class="codeContent panelContent">
<pre class="code-java">
<span class="code-keyword">import</span> java.io.IOException;

<span class="code-keyword">import</span> org.apache.cxf.attachment.AttachmentDeserializer;
<span class="code-keyword">import</span> org.apache.cxf.message.Message;
<span class="code-keyword">import</span> org.apache.cxf.phase.AbstractPhaseInterceptor;
<span class="code-keyword">import</span> org.apache.cxf.phase.Phase;

<span class="code-keyword">public</span> class AttachmentInInterceptor <span
class="code-keyword">extends</span> AbstractPhaseInterceptor&lt;Message&gt;
{
    <span class="code-keyword">public</span> AttachmentInInterceptor() {
        <span class="code-keyword">super</span>(Phase.RECEIVE);
    }

    <span class="code-keyword">public</span> void handleMessage(Message message)
{
        <span class="code-object">String</span> contentType = (<span class="code-object">String</span>)
message.get(Message.CONTENT_TYPE);
        <span class="code-keyword">if</span> (contentType != <span class="code-keyword">null</span>
&amp;&amp; contentType.toLowerCase().indexOf(<span class="code-quote">"multipart/related"</span>)
!= -1) {
            AttachmentDeserializer ad = <span class="code-keyword">new</span>
AttachmentDeserializer(message);
            <span class="code-keyword">try</span> {
                ad.initializeAttachments();
            } <span class="code-keyword">catch</span> (IOException e) {
                <span class="code-keyword">throw</span> <span class="code-keyword">new</span>
Fault(e);
            }
        }
    }

    <span class="code-keyword">public</span> void handleFault(Message messageParam)
{
    }
}
</pre>
</div></div>
<p>Extending from sub-classes of AbstractPhaseInterceptor allows your interceptor to
access more specific information than those in the Message interface. One of the sub-classes
of AbstractPhaseInterceptor is <a href="http://tinyurl.com/2xqyg6" class="external-link"
rel="nofollow">AbstractSoapInterceptor</a>.  Extending from this class allows your
interceptor to access the SOAP header and version information of the <a href="http://tinyurl.com/2gxj2c"
class="external-link" rel="nofollow">SoapMessage class</a>. For example, SoapActionInInterceptor
is used in CXF to parse the SOAP action, as a simplified version of it shows below:</p>
<div class="code panel" style="border-width: 1px;"><div class="codeContent panelContent">
<pre class="code-java">
<span class="code-keyword">import</span> java.util.Collection;
<span class="code-keyword">import</span> java.util.List;
<span class="code-keyword">import</span> java.util.Map;

<span class="code-keyword">import</span> org.apache.cxf.binding.soap.Soap11;
<span class="code-keyword">import</span> org.apache.cxf.binding.soap.Soap12;
<span class="code-keyword">import</span> org.apache.cxf.binding.soap.SoapMessage;
<span class="code-keyword">import</span> org.apache.cxf.binding.soap.model.SoapOperationInfo;
<span class="code-keyword">import</span> org.apache.cxf.endpoint.Endpoint;
<span class="code-keyword">import</span> org.apache.cxf.helpers.CastUtils;
<span class="code-keyword">import</span> org.apache.cxf.interceptor.Fault;
<span class="code-keyword">import</span> org.apache.cxf.message.Exchange;
<span class="code-keyword">import</span> org.apache.cxf.message.Message;
<span class="code-keyword">import</span> org.apache.cxf.phase.Phase;
<span class="code-keyword">import</span> org.apache.cxf.service.model.BindingOperationInfo;
<span class="code-keyword">import</span> org.apache.cxf.service.model.OperationInfo;

<span class="code-keyword">public</span> class SoapActionInInterceptor <span
class="code-keyword">extends</span> AbstractSoapInterceptor {

    <span class="code-keyword">public</span> SoapActionInInterceptor() {
        <span class="code-keyword">super</span>(Phase.READ);
        addAfter(ReadHeadersInterceptor.class.getName());
        addAfter(EndpointSelectionInterceptor.class.getName());
    }

    <span class="code-keyword">public</span> void handleMessage(SoapMessage message)
<span class="code-keyword">throws</span> Fault {
        <span class="code-keyword">if</span> (message.getVersion() <span class="code-keyword">instanceof</span>
Soap11) {
            Map&lt;<span class="code-object">String</span>, List&lt;<span
class="code-object">String</span>&gt;&gt; headers = CastUtils.<span class="code-keyword">cast</span>((Map)message.get(Message.PROTOCOL_HEADERS));
            <span class="code-keyword">if</span> (headers != <span class="code-keyword">null</span>)
{
                List&lt;<span class="code-object">String</span>&gt; sa
= headers.get(<span class="code-quote">"SOAPAction"</span>);
                <span class="code-keyword">if</span> (sa != <span class="code-keyword">null</span>
&amp;&amp; sa.size() &gt; 0) {
                    <span class="code-object">String</span> action = sa.get(0);
                    <span class="code-keyword">if</span> (action.startsWith(<span
class="code-quote">"\"</span>")) {
                        action = action.substring(1, action.length() - 1);
                    }
                    getAndSetOperation(message, action);
                }
            }
        } <span class="code-keyword">else</span> <span class="code-keyword">if</span>
(message.getVersion() <span class="code-keyword">instanceof</span> Soap12) {
          ...........
        }
    }

    <span class="code-keyword">private</span> void getAndSetOperation(SoapMessage
message, <span class="code-object">String</span> action) {
        <span class="code-keyword">if</span> ("".equals(action)) {
            <span class="code-keyword">return</span>;
        }

        Exchange ex = message.getExchange();
        Endpoint ep = ex.get(Endpoint.class);

        BindingOperationInfo bindingOp = <span class="code-keyword">null</span>;

        Collection&lt;BindingOperationInfo&gt; bops = ep.getBinding().getBindingInfo().getOperations();
        <span class="code-keyword">for</span> (BindingOperationInfo boi : bops)
{
            SoapOperationInfo soi = (SoapOperationInfo) boi.getExtensor(SoapOperationInfo.class);
            <span class="code-keyword">if</span> (soi != <span class="code-keyword">null</span>
&amp;&amp; soi.getAction().equals(action)) {
                <span class="code-keyword">if</span> (bindingOp != <span class="code-keyword">null</span>)
{
                    <span class="code-comment">//more than one op with the same action,
will need to parse normally
</span>                    <span class="code-keyword">return</span>;
                }
                bindingOp = boi;
            }
        }
        <span class="code-keyword">if</span> (bindingOp != <span class="code-keyword">null</span>)
{
            ex.put(BindingOperationInfo.class, bindingOp);
            ex.put(OperationInfo.class, bindingOp.getOperationInfo());
        }
    }

}
</pre>
</div></div>
<p>Note that you will need to specify the phase that the interceptor will be included
in. This is done in the interceptor's constructor:</p>
<div class="code panel" style="border-width: 1px;"><div class="codeContent panelContent">
<pre class="code-java">
<span class="code-keyword">public</span> class MyInterceptor <span class="code-keyword">extends</span>
AbstractSoapInterceptor {
  <span class="code-keyword">public</span> MyInterceptor() {
    <span class="code-keyword">super</span>(Phase.USER_PROTOCOL);
  }
  ...
}
</pre>
</div></div>
<p>You can also express that you would like the interceptor to run before/after certain
other interceptors defined in the same phase:</p>
<div class="code panel" style="border-width: 1px;"><div class="codeContent panelContent">
<pre class="code-java">
<span class="code-keyword">public</span> class MyInterceptor <span class="code-keyword">extends</span>
AbstractSoapInterceptor {
  <span class="code-keyword">public</span> MyInterceptor() {
    <span class="code-keyword">super</span>(Phase.USER_PROTOCOL);

    <span class="code-comment">// MyInterceptor needs to run after SomeOtherInterceptor
</span>    getAfter().add(SomeOtherInterceptor.class.getName());

    <span class="code-comment">// MyInterceptor needs to run before YetAnotherInterceptor
</span>    getBefore().add(YetAnotherInterceptor.class.getName());
  }
  ...
}
</pre>
</div></div>
<p>You can add your interceptors into the interceptor chain either programmatically
or through configuration.</p>

<h2><a name="Interceptors-Addinginterceptorsprogrammatically"></a>Adding
interceptors programmatically</h2>

<p>To add this to your server, you'll want to get access to the Server object (see <a
href="/confluence/display/CXF20DOC/Server%2C+Service%2C+and+Client+FactoryBeans" title="Server,
Service, and Client FactoryBeans">here</a> for more info):</p>
<div class="code panel" style="border-width: 1px;"><div class="codeContent panelContent">
<pre class="code-java">
<span class="code-keyword">import</span> org.apache.cxf.endpoint.Server;
<span class="code-keyword">import</span> org.apache.cxf.frontend.ServerFactoryBean;
...

MyInterceptor myInterceptor = <span class="code-keyword">new</span> MyInterceptor();

Server server = serverFactoryBean.create();
server.getEndpoint().getInInterceptor().add(myInterceptor);
</pre>
</div></div>

<p>On the Client side the process is very similar:</p>
<div class="code panel" style="border-width: 1px;"><div class="codeContent panelContent">
<pre class="code-java">
<span class="code-keyword">import</span> org.apache.cxf.endpoint.Client;
<span class="code-keyword">import</span> org.apache.cxf.frontend.ClientProxy;
...

MyInterceptor myInterceptor = <span class="code-keyword">new</span> MyInterceptor();
FooService client = ... ; <span class="code-comment">// created from ClientProxyFactoryBean
or generated JAX-WS client
</span>
<span class="code-comment">//You could also call clientProxyFactroyBean.getInInterceptor().add(myInterceptor)
to add the interceptor
</span>
Client cxfClient = ClientProxy.getClient(client);
cxfClient.getInInterceptors().add(myInterceptor);

<span class="code-comment">// then you can call the service
</span>client.doSomething();
</pre>
</div></div>

<p>You can also use annotation to add the interceptors from the SEI or service class.
When CXF create the server or client, CXF will add the interceptor according with the annotation.</p>
<div class="code panel" style="border-width: 1px;"><div class="codeContent panelContent">
<pre class="code-java">
@org.apache.cxf.interceptor.InInterceptors (interceptors = {<span class="code-quote">"com.example.Test1Interceptor"</span>
})
@org.apache.cxf.interceptor.InFaultInterceptors (interceptors = {<span class="code-quote">"com.example.Test2Interceptor"</span>
})
@org.apache.cxf.interceptor.OutInterceptors (interceptors = {<span class="code-quote">"com.example.Test1Interceptor"</span>
})
@org.apache.cxf.interceptor.InFaultInterceptors (interceptors = {<span class="code-quote">"com.example.Test2Interceptor"</span>,<span
class="code-quote">"com.example.Test3Intercetpor"</span> })
@WebService(endpointInterface = <span class="code-quote">"org.apache.cxf.javascript.fortest.SimpleDocLitBare"</span>,
            targetNamespace = <span class="code-quote">"uri:org.apache.cxf.javascript.fortest"</span>)
<span class="code-keyword">public</span> class SayHiImplementation <span class="code-keyword">implements</span>
SayHi {
   <span class="code-keyword">public</span> <span class="code-object">long</span>
sayHi(<span class="code-object">long</span> arg) {
       <span class="code-keyword">return</span> arg;
   }
   ...
}
</pre>
</div></div>

<h2><a name="Interceptors-Addinginterceptorsthroughconfiguration"></a>Adding
interceptors through configuration</h2>

<p>The <a href="/confluence/display/CXF20DOC/Configuration" title="Configuration">configuration
file</a> page provides examples on using configuration files to add interceptors.</p>

<p>Adding MyInterceptor to the bus:</p>
<div class="code panel" style="border-width: 1px;"><div class="codeContent panelContent">
<pre class="code-xml">
&lt;beans xmlns=<span class="code-quote">"http://www.springframework.org/schema/beans"</span>
       <span class="code-keyword">xmlns:xsi</span>=<span class="code-quote">"http://www.w3.org/2001/XMLSchema-instance"</span>
       <span class="code-keyword">xmlns:cxf</span>=<span class="code-quote">"http://cxf.apache.org/core"</span>
       xsi:schemaLocation="
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
http://cxf.apache.org/core http://cxf.apache.org/schemas/core.xsd"&gt;

    <span class="code-tag">&lt;bean id=<span class="code-quote">"MyInterceptor"</span>
class=<span class="code-quote">"demo.interceptor.MyInterceptor"</span>/&gt;</span>

    <span class="code-tag"><span class="code-comment">&lt;!-- We are adding
the interceptors to the bus as we will have only one endpoint/service/bus. --&gt;</span></span>

    <span class="code-tag">&lt;cxf:bus&gt;</span>
        <span class="code-tag">&lt;cxf:inInterceptors&gt;</span>
            <span class="code-tag">&lt;ref bean=<span class="code-quote">"MyInterceptor"</span>/&gt;</span>
        <span class="code-tag">&lt;/cxf:inInterceptors&gt;</span>
        <span class="code-tag">&lt;cxf:outInterceptors&gt;</span>
            <span class="code-tag">&lt;ref bean=<span class="code-quote">"MyInterceptor"</span>/&gt;</span>
       <span class="code-tag">&lt;/cxf:outInterceptors&gt;</span>
    <span class="code-tag">&lt;/cxf:bus&gt;</span>
<span class="code-tag">&lt;/beans&gt;</span>

</pre>
</div></div>

<p>For embedded Jetty-based web services, the configuration file can be declared by
starting the service with the -Dcxf.config.file=server.xml option.  See the <a href="http://tinyurl.com/2c9fuf"
class="external-link" rel="nofollow">server configuration</a> section on the configuration
file page for information on specifying the file for servlet WAR file-based web service implementations.</p>

<p>Adding MyInterceptor to your client:</p>
<div class="code panel" style="border-width: 1px;"><div class="codeContent panelContent">
<pre class="code-xml">
&lt;beans xmlns=<span class="code-quote">"http://www.springframework.org/schema/beans"</span>
       <span class="code-keyword">xmlns:xsi</span>=<span class="code-quote">"http://www.w3.org/2001/XMLSchema-instance"</span>
       <span class="code-keyword">xmlns:http</span>=<span class="code-quote">"http://cxf.apache.org/transports/http/configuration"</span>
       xsi:schemaLocation="http://cxf.apache.org/transports/http/configuration http://cxf.apache.org/schemas/configuration/http-conf.xsd
       http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd"&gt;

    <span class="code-tag">&lt;http:conduit name=<span class="code-quote">"{http://apache.org/hello_world_soap_http}SoapPort9001.http-conduit"</span>&gt;</span>
      <span class="code-tag">&lt;http:client DecoupledEndpoint=<span class="code-quote">"http://localhost:9990/decoupled_endpoint"</span>/&gt;</span>
    <span class="code-tag">&lt;/http:conduit&gt;</span>

    <span class="code-tag">&lt;bean id=<span class="code-quote">"MyInterceptor"</span>
class=<span class="code-quote">"demo.interceptor.MyInterceptor"</span>/&gt;</span>

    <span class="code-tag"><span class="code-comment">&lt;!-- We are adding
the interceptors to the bus as we will have only one endpoint/service/bus. --&gt;</span></span>

    <span class="code-tag">&lt;bean id=<span class="code-quote">"cxf"</span>
class=<span class="code-quote">"org.apache.cxf.bus.CXFBusImpl"</span>&gt;</span>
        <span class="code-tag">&lt;property name=<span class="code-quote">"inInterceptors"</span>&gt;</span>
            <span class="code-tag">&lt;ref bean=<span class="code-quote">"MyInterceptor"</span>/&gt;</span>
        <span class="code-tag">&lt;/property&gt;</span>
        <span class="code-tag">&lt;property name=<span class="code-quote">"outInterceptors"</span>&gt;</span>
            <span class="code-tag">&lt;ref bean=<span class="code-quote">"MyInterceptor"</span>/&gt;</span>
        <span class="code-tag">&lt;/property&gt;</span>
    <span class="code-tag">&lt;/bean&gt;</span>
<span class="code-tag">&lt;/beans&gt;</span>
</pre>
</div></div>

<p>To specify the client-side configuration file, start your client using the -Dcxf.config.file=client.xml
option.</p>



<h2><a name="Interceptors-CXFcontributedinterceptors"></a>CXF contributed
interceptors</h2>
<p>In CXF, all the functionality of processing messages is done via interceptors.  
Thus, when debugging a message flow, you will come across a bunch of interceptors in the chain.
  Here is a list of some of the common interceptors and the functionality they provide.  The
source code for these interceptors (latest trunk version) can be viewed with <a href="http://tinyurl.com/y65b5x3"
class="external-link" rel="nofollow">this Fisheye query</a>.</p>


<h4><a name="Interceptors-DefaultJAXWSIncominginterceptorchain%28Server%29%3A"></a>Default
JAX-WS Incoming interceptor chain (Server):</h4>
<ul>
	<li><b>AttachmentInInterceptor</b> Parse the mime headers for mime boundaries,
finds the "root" part and resets the input stream to it, and stores the other parts in a collection
of Attachments</li>
	<li><b>StaxInInterceptor</b> 	Creates an XMLStreamReader from the transport
InputStream on the Message</li>
	<li><b>ReadHeadersInterceptor</b>  Parses the SOAP headers and stores them
on the Message</li>
	<li><b>SoapActionInInterceptor</b> Parses "soapaction" header and looks
up the operation if a unique operation can be found for that action.</li>
	<li><b>MustUnderstandInterceptor</b> 	Checks the MustUnderstand headers,
its applicability and process it, if required</li>
	<li><b>SOAPHandlerInterceptor</b> SOAP Handler as per JAX-WS</li>
	<li><b>LogicalHandlerInInterceptor</b> Logical Handler as per JAX-WS</li>
	<li><b>CheckFaultInterceptor</b>  Checks for fault, if present aborts interceptor
chain and invokes fault handler chain</li>
	<li><b>URIMappingInterceptor</b> Can handle HTTP GET, extracts operation
info and sets the same in the Message</li>
	<li><b>DocLiteralnInterceptor</b> Examines the first element in the SOAP
body to determine the appropriate Operation (if soapAction did not find one) and calls the
Databinding to read in the data.</li>
	<li><b>SoapHeaderInterceptor</b> Perform databinding of the SOAP headers
for headers that are mapped to parameters</li>
	<li><b>WrapperClassInInterceptor</b> For wrapped doc/lit, the DocLiteralInInterceptor
probably read in a single JAXB bean.  This interceptor pulls the individual parts out of that
bean to construct the Object[] needed to invoke the service.</li>
	<li><b>SwAInInterceptor</b> For Soap w/ Attachments, finds the appropriate
attachments and assigns them to the correct spot in the parameter list.</li>
	<li><b>HolderInInterceptor</b> For OUT and IN/OUT parameters, JAX-WS needs
to create Holder objects.   This interceptor creates the Holders and puts them in the parameter
list.</li>
	<li><b>ServiceInvokerInInterceptor</b> Actually invokes the service.</li>
</ul>



<h3><a name="Interceptors-DefaultOutgoingchainstack%28Server%29%3A"></a>Default
Outgoing chain stack (Server):</h3>
<ul>
	<li><b>HolderOutInterceptor</b> For OUT and IN/OUT params, pulls the values
out of the JAX-WS Holder objects (created in HolderInInterceptor) and adds them to the param
list for the out message.</li>
	<li><b>SwAOutInterceptor</b> For OUT parts that are Soap attachments, pulls
them from the list and holds them for later.</li>
	<li><b>WrapperClassOutInterceptor</b> For doc/lit wrapped, takes the remaining
parts and creates a wrapper JAXB bean to represent the whole message.</li>
	<li><b>SoapHeaderOutFilterInterceptor</b>  Removes inbound marked headers</li>
	<li><b>SoapActionOutInterceptor</b> Sets the SOAP Action</li>
	<li><b>MessageSenderInterceptor</b> Calls back to the Destination object
to have it setup the output streams, headers, etc... to prepare the outgoing transport.</li>
	<li><b>SoapPreProtocolOutInterceptor</b>  This interceptor is responsible
for setting up the SOAP version and header, so that this is available to any pre-protocol
interceptors that require these to be available.</li>
	<li><b>AttachmentOutInterceptor</b> If this service uses attachments (either
SwA or if MTOM is enabled), it sets up the Attachment marshallers and the mime stuff that
is needed.</li>
	<li><b>StaxOutInterceptor</b> 	Creates an XMLStreamWriter from the OutputStream
on the Message.</li>
	<li><b>SoapHandlerInterceptor</b> JAX-WS SOAPHandler</li>
	<li><b>SoapOutInterceptor</b> 	Writes start element for soap:envelope and
complete elements for other header blocks in the message. Adds start element for soap:body
too.</li>
	<li><b>LogicalHandlerOutInterceptor</b> JAX-WS Logical handler stuff</li>
	<li><b>WrapperOutInterceptor</b> If wrapped doc/lit and not using a wrapper
bean or if RPC lit, outputs the wrapper element to the stream.</li>
	<li><b>BareOutInterceptor</b> Uses the databinding to write the params
out.</li>
	<li><b>SoapOutInterceptor$SoapOutEndingInterceptor</b> Closes the soap:body
and soap:envelope</li>
	<li><b>StaxOutInterceptor$StaxOutEndingInterceptor</b> Flushes the stax
stream.</li>
	<li><b>MessageSenderInt$MessageSenderEnding</b> Closes the exchange, lets
the transport know everything is done and should be flushed to the client.</li>
</ul>


    </div>
        <div id="commentsSection" class="wiki-content pageSection">
        <div style="float: right;">
            <a href="https://cwiki.apache.org/confluence/users/viewnotifications.action"
class="grey">Change Notification Preferences</a>
        </div>
        <a href="https://cwiki.apache.org/confluence/display/CXF20DOC/Interceptors">View
Online</a>
        |
        <a href="https://cwiki.apache.org/confluence/pages/diffpagesbyversion.action?pageId=49956&revisedVersion=29&originalVersion=28">View
Changes</a>
                |
        <a href="https://cwiki.apache.org/confluence/display/CXF20DOC/Interceptors?showComments=true&amp;showCommentArea=true#addcomment">Add
Comment</a>
            </div>
</div>
</div>
</div>
</div>
</body>
</html>

Mime
View raw message