
Signing Messages with XSS4J
In the first column of this series we introduced the WSS4J API. In the second column we demonstrated the use of XSS4J for XML encryption. In the third column we implemented encryption features of WSS4J using the concepts discussed in the second column.
This column will examine the implementation of the reference list only token that we introduced in Listing 4 of the third column, as well as the use of XSS4J to sign XML messages.
Implementing the reference list only token
As you may recall from the third column, implementing a particular token needs two steps:
- Implement the Token interface to reflect the functionality of the token.
-
Add token-specific handling in the
encrypt()method of theWSSMessageclass.
You can refer to Listing 4 of the previous column to see the format of the WSS message that a reference list only token will create.
Listing 1 shows
the ReferenceListOnlyToken class which implements
the Token interface for reference list only
token. The ReferenceListOnlyToken implementation is
similar to the EncryptedKeyToken implementation that we
presented in Listing
5 of the previous column. You can compare Listing 1 of this column with Listing
5 of the previous column. You will notice that
the ReferenceListOnlyToken class is simpler than
the EncryptedKeyToken class. Notice the following points
from Listing 1:
-
This time we are not using the
KeyStoreKeyInfoResolverobject because we don't want to include any encrypted key. Here we just need to wrap the name of the key inside the KeyInfo-KeyName pair. We can easily do it using DOM, so there's no need to use theKeyStoreKeyInfoResolverobject. -
The encryption template (Listing
2) that we are using for the reference list only token contains
the KeyInfo-KeyName pair. The
ReferenceListOnlyTokenconstructor authors the name of the encryption key as contents of the KeyName element. -
The encrypt() method in Listing 1
performs the actual encryption. The process of encryption is similar
to the
EncryptedKeyToken.encrypt()method in Listing 5 of the previous column, except that Listing 1 does not use theKeyStoreKeyInfoResolverobject. Recall that step 6 of theencrypt()method (Listing 5 of the third column) made a call to theEncryptionContext.setKeyInfoResolver()method. Now in Listing 1, theencrypt()method of theReferenceListOnlyTokenclass makes a call to theEncryptionContext.setKey()method. This is because we are not using theKeyStoreKeyInfoResolverclass and therefore we need to provide the key directly to theEncryptionContextclass. -
The
getXMLString()method in Listing 1 authors the actual token (aReferenceListelement, as shown in Listing 4 of the previous column). Notice that thegetXMLString()method of Listing 1 authors the token from scratch. While in theEncryptedKeyToken.getXMLString()method (Listing 5 of the previous column), the token was part of the encryption template, and we extracted the token from theEncryptedDataelement in step 7 of theencrypt()method. You can see that authoring aReferenceListOnlyTokenis simpler than authoring theEncryptedKeyToken.
Listing 3 shows an enhanced
version of the WSSMessage class, which includes support
for ReferenceListOnly token, in addition to the tokens
that we implemented in the previous column.
Listing 4 is a small sample
application that shows how you will use
the ReferenceListOnly token in a Java application. The
use is exactly the same as before:
-
Instantiate a
WSSMessageobject. -
Instantiate a
Tokenimplementation and call itssetSecret()method. -
Call the
encryptElement()method of theWSSMessageobject that you created in step 1.
Using XSS4J for XML Digital Signature
We are now going to demonstrate how to use XSS4J to produce XML digital signatures. We have already discussed all details of the XML Digital Signature syntax in the second article of my series on Web services security.
We will use the following different types of KeyInfo elements in our demonstration:
- KeyInfo element that wraps an X.509 certificate
- KeyInfo element that wraps pointers to an X.509 certificate
- KeyInfo element that wraps the name of a key
We are going to sign the first Parameter element of the XML file shown in Listing 5. After signing, the resulting XML will look like as shown in Listing 6.
Notice that the signature that we are going to produce is detached from the element that we signed. Refer to the three types of XML digital signatures (enveloping, enveloped, and detached) that we discussed in the "Message Integrity and User Authentication with XML Signatures" section of second article of my Web services security series.
We are going to demonstrate the use of XSS4J to produce detached signatures. This is because WSS only allows detached type of XML signatures in WSS messages.
The XMLDSigSampleWithCertificate class that we have shown
in Listing 7 shows how to use
XSS4J to produce detached Signatures. We have hard-coded the following
parameters in Listing 7:
-
keyStorePathis the full path name of a key store file. The key store file contains the certificate that we going to use in our sample application. The source code download of this column contains a generateCertificate.bat file that shows how you can generate a certificate to try our sample application. -
aliasis the string representing the name of the certificate in the key store that we are going to use in our sample signature application. -
storePassis the string representation of the password that we need in order to access the key store. -
keyPassis the string representation of the password that we need in order to access the private key in the key store. -
signatureTemplateFileis the name of the template file (Listing 8) that we are going to use for signature. You can compare Listing 8 with Listing 6 and you will find that the template does not contain the digest and signature values. These values will be filled in during the signature process. Also notice that the signature template does not contain a KeyInfo element. That's because we will author a KeyInfo element programmatically and append the same into the template. -
inputFileis the string containing name of the input XML file (Listing 5). -
outputFileis the string containing name of the output XML file, which shows the result of signature operation (Listing 6).
You can find the following simple steps in Listing 7:
Step 1: Load the input XML file in a DOM Document object named inputDoc.
Step 2: From the DOM document of step 1, find the element to be
signed. We are simply going to sign the first Parameter child of
the GetSpecialDiscountedBookingForPartnersResponse
element of Listing 5, so the
second step in the XMLDSigSampleWithCertificate class
of Listing 7 is to fetch the
root element of the input XML file (which is
the GetSpecialDiscountedBookingForPartnersResponse
element) and then fetch its first child element (which is the
Parameter element that we are going to sign).
Step 3: After loading the element to be signed in a DOM element
object, we have also fetched the "Id" attribute value of the element
to be signed and stored the value in a variable
named elementToBeSignedId. We will (later in step 5) use
this value to refer from the Signature element to the element that we
are going to sign.
Step 4: Load the signature template (Listing 8) in a DOM document
named templateDoc and then extract the Signature element
from the templateDoc. We have stored the Signature
element in a DOM Element object
named templateElement. Note that we have imported
the templateElement into the inputDoc and
placed it as a child of
the GetSpecialDiscountedBookingForPartnersResponse
element. Now the template Signature element is at its correct place in
the input XML file. The signature process will only fill the template
with actual signature data.
Step 5: Now we can set the id attribute value (that we fetched
in step 3 above) as the value of the URI attribute of
the Reference element. Notice from the Signature template
of Listing 8 that there is a
Reference child element of the Signature
element. The Reference element has an attribute
named URI, whose value we have not mentioned in the
template because we want to set this value
dynamically. This URI attribute is used to refer from the
Signature to the element that we are signing. For details of how
the URI attribute works, please refer to point number 1
of the "Four Steps to XML Digital Signature Authoring" section of
the second
article of my series on web services security.
Step 6: Next we get an instance of the KeyStore
class and load a key store file into the KeyStore
object. Here we are assuming that the key store file contains a
certificate named "myTourOperatorCertificate". So we
simply call the getCertificate() method of the key store
object, which returns an X509Certificate
instance. The X509Certificate instance wraps the tour
operator's certificate. After loading the tour operator's certificate
in an X509Certificate object, we also fetch the public
key of the tour operator and load it into a Key object.
Pages: 1, 2 |