XFire

Home
Bug/Issue Reporting
Download
FAQ
Get Involved
License
News
Stack Comparison
Support
User's Guide
XFire Team

M5

Javadocs
Reports

M6-SNAPSHOT

Javadocs
Reports

Developers

Developer Space
CVS
Building
Architecture
Interesting Projects
Release Process

Steps to implementing WS-Security...

1. Determine how to use the TSIK API
This will be our "hello world" starting point. Figure out how to take a soap document on the file system, encrypt it and decrypt it via the TSIK api so we get an understanding of how to use it.

2. Try it with a document which streams in
Download the code at https://stax2dom.dev.java.net/ and figure out how to use it. You'll need to start with an XMLStreamReader and end up with a document. Pseudocode:

XMLInputFactory factory = XMLInputFactory.getInstance();
XMLStreamReader reader = factory.createXMLStreamReader(inputStreamToFile);

....
// somehow take the reader and create a Document with the above library.
org.w3c.dom.Document doc = ...

3. Create a DocumentXMLStreamReader
In this step we're going to forget about encryption and decryption. After decryption we'll end up with a org.w3c.dom.Document. But XFire expects an XMLStreamReader javadoc. So we need to convert between the two.

public class DocumentXMLStreamReader
    implements XMLStreamReader
{
  public DocumentXMLStreamReader(org.w3c.dom.Document doc)
  {
   ....
  }

  public int next()
  {
    // this would get events as it progressed down the document.
  }
....
}

I've done this before with the XOM xml toolkit. Check out this example. There is also a unit test which shows how to use it.

4. Tie it into XFire
We're going to write a Handler which does the following

  1. takes the incoming XMLStreamReader, reads it into a document
  2. Decrypts the document
  3. Creates another XMLStreamReader from the document

Here's a little pseudo code:

public class WSSecurityInHandler
  extends AbstractHandler
{
  public String getPhase()
  {
    Phase.PARSE;
  }
  public void invoke(MessageContext context)
  {
    Document doc = createDoc(context.getInMessage().getXMLStreamReader);
    decrypt(doc);
    XMLStreamReader reader = createStream(doc);
    context.getInMessage().setXMLStreamReader(reader);
  }
}

A test service:

public class Echo
{
  public String echo(string echo)
  {
    return echo;
  }
}

and a unit test:

public class WSSecurityTest
  extends AbstractXFireTest
{
  Service service;

  public void setUp()
  {
    // Creates a service from the echo class
    service = getServiceFactory().create(Echo.class);

    // Registers it
    getServiceRegistry().register(service);

    // Add in a WS-Security Handler
    service.addInHandler(new WSSecurityHandler());
  }

  public void testService()
  {
    // sends a message to your service. the handler intercepts the document and decrypts
    org.codehaus.yom.Document response = 
      invokeService("Echo", "/encrypted/document/on/the/classpath.xml");

    // prints the response to System.out
    printNode(response);

    // Checks to make sure we get the echo'd response
    addNamespace("e", service.getServiceInfo().getName().getNamespace());
    assertValid("//e:echoResponse", response);
  }
}

The "/encrypted/document/on/the/classpath.xml" needs to be an encrypted version of this document which the WS-SecurityHandler can understand:

<env:Envelope xmlns:env="http://schemas.xmlsoap.org/soap/envelope/">
 <env:Body>
  <m:echo xmlns:m="NAMESPACE">
   <m:in0>Yo Yo</m:in0>
  </m:echo>
 </env:Body>
</env:Envelope>

where NAMESPACE is the namespace of your service. The namespace is constructed from the pacakge name. You can easily view this by adding a

System.out.println(service.getServiceInfo().getName().getNamespace());

to the above test.