Skip to main content

Extending JAX-WS With Annotations

Posted by ramapulavarthi on January 16, 2007 at 9:31 AM PST

As you know JAX-WS 2.1 is the re-architected version of JAX-WS 2.0 with
high performance and additional features supporting JAX-WS 2.1 Spec. It
provides a lot of
extension points for developers  to utilize the plug-in
mechansim
to modify/extend the default JAX-WS behavior. These extension points
can be used at Tool time as well as Runtime. See href="https://jax-ws-architecture-document.dev.java.net/nonav/doc21/?jaxws/package-summary.html">JAX-WS
2.1 Architecture document for more details.



Extension Points:

I will briefly go over some of the extension points and concentrate
more on extending using Java annotations and leave others for you to
explore.


style="font-weight: bold;">Tube: Tube is a
filter that
lets you work on the Packet ( an abstraction of Message with context)
and pass it on to the next tube in the chain. You can think of it like
a Handler but has efficient access to the Message through different
API. Tubes can run asynchronusly, which means request packet and
response packet can be processed by different threads.See href="https://jax-ws-architecture-document.dev.java.net/nonav/doc21/com/sun/xml/ws/api/pipe/Tube.html">Tube
documentation for more details.



WSDLGeneratorExtension:
WSDLGenerator uses Service finder mechanism to discover
WSDLGeneratorExtensions and calls them to contribute in the generation
of WSDL. See href="https://jax-ws-architecture-document.dev.java.net/nonav/doc21/com/sun/xml/ws/api/wsdl/writer/WSDLGeneratorExtension.html">WSDLGeneratorExtension
documentation for more details.



WSDLParserExtension:
These
extensions are called by WSDL Parser at runtime to process the WSDL
extensibility elements in the wsdl definitions. For example,
W3CAddressingWSDLParserExtension in RI uses this to process
<wsaw:UsingAddressing> extensibility element in
wsdl:binding and
wsdl:portType definitions. See href="https://jax-ws-architecture-document.dev.java.net/nonav/doc21/com/sun/xml/ws/api/wsdl/parser/WSDLParserExtension.html">WSDLParserExtension
documentation for more details documentation for
more details.



Web Service Features:

For these various extensions to be picked up and used at runtime,
corresponding features have to enabled either through WSDL or Java
Annotations on Endpoint implementation or Programatic configuration of
features on the Client. JAX-WS 2.1 Specification introduces
WebServiceFeature
and WebServiceFeatureAnnotation
to specify features
on a client and endpoint implementation. In 2.1 RI, It uses this Web
Service  feature mechanism to support W3C Addressing using
@Addressing and AddressingFeature



Writing Custom Web
Service Feature:


One can use similar mechanism to extend JAX-WS by defining custom
annotations and its bean representation to be used by client runtime.
Annotations are used on the endpoint implementation class where as
features in bean form are used on client-side. For this to work, the
custom annotations should follow these rules.

  • Define custom feature annotation which uses
    @WebServiceFeatureAnnotation and specify the WebServiceFeature bean
  • Define a feature that extends WebServiceFeature so that it
    can be used by Client
  • Mark one of the constructors in the bean as href="http://fisheye5.cenqua.com/browse/jax-ws-sources/jaxws-ri/rt/src/com/sun/xml/ws/api/FeatureConstructor.java">@FeatureConstructor.
    This is needed because Reflection does n't capture the parameters names
    at runtime, this is needed for JAX-WS to recognize the custom
    annotations in to its bean representation.

Feature annotations specified on endpoint implementation class are
available as features on href="https://jax-ws-architecture-document.dev.java.net/nonav/doc21/com/sun/xml/ws/api/WSBinding.html">WSBinding
(an implementation of
javax.xml.ws.Binding) which is available to almost all extension
points.



Examples:

In the following example, I will show you how one can utilize this
extension mechanism.



Although W3C Addressing Specification is a recommendation, Some still
use Member Submision version of addressing. To support this, there is a
RI specific feature href="https://jax-ws-architecture-document.dev.java.net/nonav/doc21/com/sun/xml/ws/developer/MemberSubmissionAddressing.html">@MemberSubmissionAddressing.
Look closely at @MemberSubmissionAddressing class. It uses to
href="https://jax-ws-architecture-document.dev.java.net/nonav/doc21/com/sun/xml/ws/developer/MemberSubmissionAddressingFeature.html">MemberSubmissionAddressingFeature
as bean, which can be used on
client-side to enable the feature.



@WebServiceFeatureAnnotation(id=
MemberSubmissionAddressingFeature.ID,bean=MemberSubmissionAddressingFeature.class)


public @interface MemberSubmissionAddressing {

    /**

     * Specifies if this feature is
enabled or disabled.

     */

    boolean enabled() default true;



    /**

     * Property to determine the
value of the

     *
<code>wsdl:required</code> attribute on

     *
<code>wsaw:UsingAddressing</code> element
in the WSDL.

     */

    boolean required() default false;

}



public class MemberSubmissionAddressingFeature style="color: rgb(204, 0, 0);">extends WebServiceFeature


    /**

     * Create an
MemberSubmissionAddressingFeature

     * @param enabled specifies
whether this feature should

    
*               
be enabled or not.

     */

    public
MemberSubmissionAddressingFeature(boolean enabled) {

       
this.enabled = enabled;

    }



    /**

     * Create an
<code>MemberSubmissionAddressingFeature</code>

     * @param enabled specifies
whether this feature should

     * be enabled or not.

     * @param required specifies
the value that will be used

     * for the
<code>required</code> attribute on the

     *
<code>wsaw:UsingAddressing</code> element.

     */

    @FeatureConstructor({"enabled","required"})

    public
MemberSubmissionAddressingFeature(boolean enabled, boolean required) {

       
this.enabled = enabled;

       
this.required = required;

    }

    .............

    .............   
     

}



Notice that only one constructor has been marked with style="font-style: italic;">@FeatureConstructor
which captures the names of the parameters in the corresponding
annotation.



When a endpoint implementation is marked with
@MemberSubmissionAddressing(required=false,enabled=true), JAX-WS
Runtime makes this available to StandaloneTubelineAssembler, which
plugs in the WsaTube which validates addressing headers on incoming
messages.



Similarly, W3CAddressingWSDLGeneratorExtension checks if
AddressingFeature is enabled on WSBinding and based on its value, adds
it as wsdl extensibility element like<wsaw:UsingAddressing
wsdl:required="true"> in the binding definitions.





That's all !!!



Infact, you can write your own href="https://jax-ws-architecture-document.dev.java.net/nonav/doc21/com/sun/xml/ws/api/pipe/Tube.html">Tube
and plug it in your
href="https://jax-ws-architecture-document.dev.java.net/nonav/doc21/com/sun/xml/ws/api/pipe/TubelineAssembler.html">TubelineAssembler
if a custom feature is enabled and process the
messages that transferred through the Tube. See RI specific features
like href="https://jax-ws-architecture-document.dev.java.net/nonav/doc21/com/sun/xml/ws/developer/Stateful.html">@Stateful,
href="https://jax-ws-architecture-document.dev.java.net/nonav/doc21/com/sun/xml/ws/developer/servlet/HttpSessionScope.html">@HttpSessionScope,
href="https://jax-ws-architecture-document.dev.java.net/nonav/doc21/com/sun/xml/ws/developer/MemberSubmissionAddressing.html">@MemberSubmissionAddressing
to see
how one can utilize this mechanism.



We hope developers will find these extension points useful to extend
default JAX-WS behavior. Please send in your useful comments to
dev@jax-ws.dev.java.net


Related Topics >>

Comments

Nice post. What do you think about xsd:annotation and ...

Nice post. What do you think about xsd:annotation and xsd:documentation tags generated by java annotations? Is this possible using the same mechanism you described?