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 > JAX-RS Advanced XML
Date Thu, 31 Mar 2011 11:17: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/JAX-RS+Advanced+XML">JAX-RS
Advanced XML</a></h2>
    <h4>Page <b>edited</b> by             <a href="https://cwiki.apache.org/confluence/display/~sergey_beryozkin">Sergey
Beryozkin</a>
    </h4>
        <br/>
                         <h4>Changes (7)</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" >h1. XPath support <br> <br></td></tr>
            <tr><td class="diff-deleted-lines" style="color:#999;background-color:#fdd;text-decoration:line-through;">TODO
: Expand this section <br></td></tr>
            <tr><td class="diff-added-lines" style="background-color: #dfd;">XPath
is supported on the server and client sides with the help of [XMLSource|http://svn.apache.org/repos/asf/cxf/trunk/rt/frontend/jaxrs/src/main/java/org/apache/cxf/jaxrs/ext/xml/XMLSource.java]
utility and [XPathProvider|http://svn.apache.org/repos/asf/cxf/trunk/rt/frontend/jaxrs/src/main/java/org/apache/cxf/jaxrs/provider/XPathProvider.java]
provider classes. The difference between the two is that XPathProvider allows for specifying
the XPath expressions in the external configuration. <br></td></tr>
            <tr><td class="diff-unchanged" > <br></td></tr>
            <tr><td class="diff-deleted-lines" style="color:#999;background-color:#fdd;text-decoration:line-through;">XPath
is supported on the server and client sides with the help of [XMLSource|http://svn.apache.org/repos/asf/cxf/trunk/rt/frontend/jaxrs/src/main/java/org/apache/cxf/jaxrs/ext/xml/XMLSource.java]
utility class. Please see [this section|http://cxf.apache.org/docs/jax-rs-client-api.html#JAX-RSClientAPI-XMLcentricclients]
on how http-centric WebClients can use XPath, and here is an example for the server side:
<br></td></tr>
            <tr><td class="diff-added-lines" style="background-color: #dfd;">h2.
Introduction <br></td></tr>
            <tr><td class="diff-unchanged" > <br></td></tr>
            <tr><td class="diff-added-lines" style="background-color: #dfd;">XMLSource
allows for converting matched XML DOM element, attribute and text nodes into typed complex
and primitive classes. DOM Node and Element classes as well as JAXP Source and DOMSource can
also be used. A single XMLSource instance can be used to query the same input source multiple
times if the buffering mode is enabled. <br> <br>Here are some examples: <br>
<br></td></tr>
            <tr><td class="diff-unchanged" >{code:java} <br></td></tr>
            <tr><td class="diff-added-lines" style="background-color: #dfd;">InputStream
is = new ByteArrayInputStream(&quot;&lt;foo&gt;&lt;bar attr=\&quot;3\&quot;&gt;barValue&lt;/bar&gt;&lt;/foo&gt;&quot;.getBytes());
<br>XMLSource xp = new XMLSource(is); <br>xp.setBuffering(true); <br>//
query 1 <br>String value = xp.getValue(&quot;/foo/bar/@attr&quot;); <br>assertEquals(&quot;3&quot;,
value); <br> <br>// query 2 <br>Integer intValue = xp.getNode(&quot;/foo/bar/@attr&quot;,
Integer.class); <br>assertEquals(3, intValue); <br> <br>// query 3 <br>Node
node = xp.getNode(&quot;/foo/bar/@attr&quot;, Node.class); <br>assertEquals(&quot;3&quot;,
node.getTextValue()); <br>{code} <br> <br>In the above example a primitive
attribute node is accessed in a number of ways, using the same XMLSource instance.  <br>Matched
XML complex (element) nodes can be converted in a similar way: <br> <br>{code:java}
<br>public class Bar { <br>    @XmlAttribute <br>    private String attr;
  <br>    public String getAttribute() { <br>        return attr; <br> 
  }  <br>} <br> <br>InputStream is = new ByteArrayInputStream(&quot;&lt;foo&gt;&lt;bar
attr=\&quot;3\&quot;&gt;barValue&lt;/bar&gt;&lt;/foo&gt;&quot;.getBytes());
<br>XMLSource xp = new XMLSource(is); <br>xp.setBuffering(true); <br> <br>//
query 1 <br>Bar bean = xp.getNode(&quot;/foo/bar&quot;, Bar.class); <br>assertEquals(&quot;3&quot;,
bean.getAttribute()); <br> <br>// query 2 <br>String value = xp.getValue(&quot;/foo/bar&quot;);
<br>assertEquals(&quot;&lt;bar attr=\&quot;3\&quot;&gt;barValue&lt;/bar&gt;&quot;,
value); <br>{code} <br> <br>Note that JAXB is used internally to convert
the matched XML element into a class like Bar which does not have to have an @XmlRootElement
annotation. The 2nd query in the above example how a String representation of the matched
complex node can be captured. <br> <br>h2. Using XMLSource and XPathProvider in
the application code <br> <br>Please see [this section|http://cxf.apache.org/docs/jax-rs-client-api.html#JAX-RSClientAPI-XMLcentricclients]
on how http-centric WebClients can use XPath, and here is an example for the server side:
<br> <br>{code:java} <br></td></tr>
            <tr><td class="diff-unchanged" >@Path(&quot;/root&quot;) <br>public
class Root { <br></td></tr>
            <tr><td class="diff-snipped" >...<br></td></tr>
            <tr><td class="diff-unchanged" >{code}  <br> <br></td></tr>
            <tr><td class="diff-changed-lines" >Users have an option to hide XPath
expressions, by registering an <span class="diff-deleted-words"style="color:#999;background-color:#fdd;text-decoration:line-through;">[XPathProvider|http://svn.apache.org/repos/asf/cxf/trunk/rt/frontend/jaxrs/src/main/java/org/apache/cxf/jaxrs/provider/XPathProvider.java],</span>
<span class="diff-added-words"style="background-color: #dfd;">XPathProvider,</span>
either on <span class="diff-added-words"style="background-color: #dfd;">the</span>
client or server sides. For <span class="diff-changed-words">example<span class="diff-deleted-chars"style="color:#999;background-color:#fdd;text-decoration:line-through;">
</span>:</span> <br></td></tr>
            <tr><td class="diff-unchanged" > <br>{code:java} <br></td></tr>
            <tr><td class="diff-snipped" >...<br></td></tr>
    
            </table>
    </div>                            <h4>Full Content</h4>
                    <div class="notificationGreySide">
        <p><span style="font-size:2em;font-weight:bold"> JAX-RS : Advanced XML
</span></p>

<div>
<ul>
    <li><a href='#JAX-RSAdvancedXML-XPathsupport'>XPath support</a></li>
<ul>
    <li><a href='#JAX-RSAdvancedXML-Introduction'>Introduction</a></li>
    <li><a href='#JAX-RSAdvancedXML-UsingXMLSourceandXPathProviderintheapplicationcode'>Using
XMLSource and XPathProvider in the application code</a></li>
</ul>
    <li><a href='#JAX-RSAdvancedXML-XSLTsupport'>XSLT support</a></li>
</ul></div>

<h1><a name="JAX-RSAdvancedXML-XPathsupport"></a>XPath support</h1>

<p>XPath is supported on the server and client sides with the help of <a href="http://svn.apache.org/repos/asf/cxf/trunk/rt/frontend/jaxrs/src/main/java/org/apache/cxf/jaxrs/ext/xml/XMLSource.java"
class="external-link" rel="nofollow">XMLSource</a> utility and <a href="http://svn.apache.org/repos/asf/cxf/trunk/rt/frontend/jaxrs/src/main/java/org/apache/cxf/jaxrs/provider/XPathProvider.java"
class="external-link" rel="nofollow">XPathProvider</a> provider classes. The difference
between the two is that XPathProvider allows for specifying the XPath expressions in the external
configuration.</p>

<h2><a name="JAX-RSAdvancedXML-Introduction"></a>Introduction</h2>

<p>XMLSource allows for converting matched XML DOM element, attribute and text nodes
into typed complex and primitive classes. DOM Node and Element classes as well as JAXP Source
and DOMSource can also be used. A single XMLSource instance can be used to query the same
input source multiple times if the buffering mode is enabled.</p>

<p>Here are some examples:</p>

<div class="code panel" style="border-width: 1px;"><div class="codeContent panelContent">
<pre class="code-java">
InputStream is = <span class="code-keyword">new</span> ByteArrayInputStream(<span
class="code-quote">"&lt;foo&gt;&lt;bar attr=\"</span>3\<span class="code-quote">"&gt;barValue&lt;/bar&gt;&lt;/foo&gt;"</span>.getBytes());
XMLSource xp = <span class="code-keyword">new</span> XMLSource(is);
xp.setBuffering(<span class="code-keyword">true</span>);
<span class="code-comment">// query 1
</span><span class="code-object">String</span> value = xp.getValue(<span
class="code-quote">"/foo/bar/@attr"</span>);
assertEquals(<span class="code-quote">"3"</span>, value);

<span class="code-comment">// query 2
</span><span class="code-object">Integer</span> intValue = xp.getNode(<span
class="code-quote">"/foo/bar/@attr"</span>, <span class="code-object">Integer</span>.class);
assertEquals(3, intValue);

<span class="code-comment">// query 3
</span>Node node = xp.getNode(<span class="code-quote">"/foo/bar/@attr"</span>,
Node.class);
assertEquals(<span class="code-quote">"3"</span>, node.getTextValue());
</pre>
</div></div>

<p>In the above example a primitive attribute node is accessed in a number of ways,
using the same XMLSource instance. <br/>
Matched XML complex (element) nodes can be converted in a similar way:</p>

<div class="code panel" style="border-width: 1px;"><div class="codeContent panelContent">
<pre class="code-java">
<span class="code-keyword">public</span> class Bar {
    @XmlAttribute
    <span class="code-keyword">private</span> <span class="code-object">String</span>
attr;  
    <span class="code-keyword">public</span> <span class="code-object">String</span>
getAttribute() {
        <span class="code-keyword">return</span> attr;
    } 
}

InputStream is = <span class="code-keyword">new</span> ByteArrayInputStream(<span
class="code-quote">"&lt;foo&gt;&lt;bar attr=\"</span>3\<span class="code-quote">"&gt;barValue&lt;/bar&gt;&lt;/foo&gt;"</span>.getBytes());
XMLSource xp = <span class="code-keyword">new</span> XMLSource(is);
xp.setBuffering(<span class="code-keyword">true</span>);

<span class="code-comment">// query 1
</span>Bar bean = xp.getNode(<span class="code-quote">"/foo/bar"</span>,
Bar.class);
assertEquals(<span class="code-quote">"3"</span>, bean.getAttribute());
 
<span class="code-comment">// query 2
</span><span class="code-object">String</span> value = xp.getValue(<span
class="code-quote">"/foo/bar"</span>);
assertEquals(<span class="code-quote">"&lt;bar attr=\"</span>3\<span class="code-quote">"&gt;barValue&lt;/bar&gt;"</span>,
value);
</pre>
</div></div>

<p>Note that JAXB is used internally to convert the matched XML element into a class
like Bar which does not have to have an @XmlRootElement annotation. The 2nd query in the above
example how a String representation of the matched complex node can be captured.</p>

<h2><a name="JAX-RSAdvancedXML-UsingXMLSourceandXPathProviderintheapplicationcode"></a>Using
XMLSource and XPathProvider in the application code</h2>

<p>Please see <a href="http://cxf.apache.org/docs/jax-rs-client-api.html#JAX-RSClientAPI-XMLcentricclients"
class="external-link" rel="nofollow">this section</a> on how http-centric WebClients
can use XPath, and here is an example for the server side:</p>

<div class="code panel" style="border-width: 1px;"><div class="codeContent panelContent">
<pre class="code-java">
@Path(<span class="code-quote">"/root"</span>)
<span class="code-keyword">public</span> class Root {
   @POST
   <span class="code-keyword">public</span> void post(XMLSource source) {
       <span class="code-object">String</span> value = source.getProperty(<span
class="code-quote">"/books/book/@name"</span>);
   }    
}
</pre>
</div></div> 

<p>Users have an option to hide XPath expressions, by registering an XPathProvider,
either on the client or server sides. For example:</p>

<div class="code panel" style="border-width: 1px;"><div class="codeContent panelContent">
<pre class="code-java">
XPathProvider provider = <span class="code-keyword">new</span> XPathProvider();
provider.setGlobalExpression(<span class="code-quote">"/books/book[position() = 1]"</span>);
WebClient wc = WebClient.create(<span class="code-quote">"http:<span class="code-comment">//aggregated/data"</span>,
Collections.singletonList(provider));
</span>Book b = wc.get(Book.class);
</pre>
</div></div>

<h1><a name="JAX-RSAdvancedXML-XSLTsupport"></a>XSLT support</h1>

<p>TODO : Expand this section</p>

<p>XSLT is currently supported by <a href="http://svn.apache.org/repos/asf/cxf/trunk/rt/frontend/jaxrs/src/main/java/org/apache/cxf/jaxrs/provider/XSLTJaxbProvider.java"
class="external-link" rel="nofollow">XSLTJaxbProvider</a>. This provider works in
tandem with JAXB and can be used to produce pretty much any format, including non-XML ones.
Likewise, it can be used to extract XML data out of incoming XML fragments, either on the
client or server sides.</p>

<p>XSLTJaxbProvider can be configured to handle input or output data, scoped by media
types if needed. For example, one may configure it such that one template handles "application/xml"
formats only while the other one handles "application/json" writes only.</p>

<p>XSLTJaxbProvider uses an injected JAX-RS UriInfo to inject all the usual JAX-RS information
like template or query parameters into a given XSLT template.</p>

<p>For example, given this resource method definition :</p>

<div class="code panel" style="border-width: 1px;"><div class="codeContent panelContent">
<pre class="code-java">
@Path(<span class="code-quote">"/root"</span>)
<span class="code-keyword">public</span> class Root {
   @GET
   @Path(<span class="code-quote">"{id}"</span>) 
   <span class="code-keyword">public</span> Book get(@PathParam(<span class="code-quote">"id"</span>)
<span class="code-object">String</span> id, @QueryParam(<span class="code-quote">"name"</span>)
<span class="code-object">String</span> name) {
       <span class="code-keyword">return</span> getBook(id, name);
   }    
}
</pre>
</div></div>

<p>an XSLT template processing the JAXB-driven serialization of a Book instance will
have parameters with name 'id' and 'name' injected.</p>

<p>Note that when XSLTJaxbProvider is used on the client side, it may not always be
possible for template parameters be injected in cases when http-centric clients are used (as
opposed to proxies). For example :</p>

<div class="code panel" style="border-width: 1px;"><div class="codeContent panelContent">
<pre class="code-java">
WebClient client = WebClient.create(<span class="code-quote">"http:<span class="code-comment">//books"</span>);
</span>client.path(<span class="code-quote">"/store/1"</span>).get();
</pre>
</div></div>

<p>it is not possible to deduce that '1' represents a template parameter in the "/store/1"
expression. However, one can use the following code instead if '1' needs to be available to
XSLT templates :</p>

<div class="code panel" style="border-width: 1px;"><div class="codeContent panelContent">
<pre class="code-java">
WebClient client = WebClient.create(<span class="code-quote">"http:<span class="code-comment">//books"</span>);
</span>client.path(<span class="code-quote">"/store/{id}"</span>, 1).get();
</pre>
</div></div>
    </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/JAX-RS+Advanced+XML">View
Online</a>
        |
        <a href="https://cwiki.apache.org/confluence/pages/diffpagesbyversion.action?pageId=24190965&revisedVersion=3&originalVersion=2">View
Changes</a>
                |
        <a href="https://cwiki.apache.org/confluence/display/CXF20DOC/JAX-RS+Advanced+XML?showComments=true&amp;showCommentArea=true#addcomment">Add
Comment</a>
            </div>
</div>
</div>
</div>
</div>
</body>
</html>

Mime
View raw message