Creating an enveloped XML signature
Your application should perform the following steps to create an enveloped XML signature using the toolkit.
Logging the user
Log in the user with the selected credentials.
user.login(credReader, <password>);Logging the user
Instantiate a source for the keys and certificates using a com.entrust.toolkit.KeyAndCertificateSource object.
user.login(credReader, <password>);Provide a signing key and verification certificate.
PrivateKey pk = user.getSigningKey();X509Certificate cert = user.getVerificationCertificate();Set the signing key and the verification certificate.
keySource.setSigningInfo(pk, cert);Initializing the IXSIL library
Retrieve the init.properties file and initialize the IXSIL library.
iaik.ixsil.util.URI initProps = new URI(<init_properties_file_URI>);IXSILInit.init(initProps);Refer to the readme file for more information on editing the init.properties file.
etjava\examples\source\com\entrust\toolkit\examples\xml\xml_readme.htmlRefer also to the Javadoc documentation of the following class.
iaik.ixsil.init.IXSILInitReferencing the signed data
Specify the XML element in your document that is to be the parent of the <Signature> element.
String insertSignaturePositionHere = <XML_element_name>;Create the XPath expression that specifies the position of the <Signature> element.
String xpath = null;xpath = "(//" + insertSignatureHere + ")[1]";Position signaturePosition = new Position(xpath, "", 0);URI baseURI = new URI(uriTobeSigned);Configuring a SOAP document signature
If you apply an XML digital signature to a SOAP document, retrieve a DOM representation of the document to be signed.
Document doc = DOMUtils.createDocumentFromXMLInstance(isURI, baseURI, DOMUtils.VALIDATION_YES_, noNamespaceSchemaLocation, schemaLocations);See the following table for a description of each parameter.
|
Parameter |
Description |
|
isURI |
The input stream that you get by resolving the URI of the document source |
|
baseURI |
The URI that points to the XML document containing the XML signature. |
|
DOMUtils.VALIDATION_YES_ |
Specifies that a validating parser should create the DOM document. |
|
noNamespaceSchemaLocation |
The schema for elements without a namespace prefix (if a validating parser creates the DOM document). |
|
schemaLocations |
Schemas for various namespaces (if a validating parser creates the DOM document). |
Get the WS-Security namespace and prefix.
String wsSecNamespaceURI = IXSILInit.getInitProperty(IXSILConstants.INITPROP_URI_WS_SECURITY_);String wsSecPrefix = IXSILInit.getInitProperty(IXSILConstants.INITPROP_NS_PREFIX_WS_SECURITY_);Check for the existence of the SOAP Header.
Element root = doc.getDocumentElement();String soapNsUri = root.getNamespaceURI();NodeList nl = doc.getElementsByTagNameNS(soapNsUri, IXSILConstants.SOAP_HEADER_TAG_);Element security = null;Built a SOAP Header if not found.
Element header = doc.createElementNS(soapNsUri, root.getPrefix() + ":" + IXSILConstants.SOAP_HEADER_TAG_);Node oldFirst = root.getFirstChild();root.insertBefore(header, oldFirst);security = doc.createElementNS(wsSecNamespaceURI, wsSecPrefix + ":" + IXSILConstants.WS_SECURITY_TAG_);header.insertBefore(security, null);root.setAttributeNS(IXSILConstants.NAMESPACE_URI_NAMESPACES_,IXSILConstants.NAMESPACE_PREFIX_NAMESPACES_ + wsSecPrefix, wsSecNamespaceURI);Creating the signer
Create a Signer object, using the constructor that takes a Document instance.
Document doc = parser.parse(istrURI);signer = new Signer(doc, baseURI, signaturePosition);Use this constructor if your application has already parsed an existing XML source to a document and manipulated it, ensuring the toolkit does not repeat the document.
Selecting the canonicalization algorithm
Use the following class to specify the canonicalization algorithm for the signature.
iaik.ixsil.algorithms.CanonicalizationAlgorithmImplCanonicalXMLCreate a new instance.
CanonicalizationAlgorithmImplCanonicalXML c14nAlg = new CanonicalizationAlgorithmImplCanonicalXML();Set the algorithm URI.
c14nAlg.setURI(new URI("http://www.w3.org/TR/2000/WD-xml-c14n-20000907"));Set the canonicalization algorithm.
signedInfo.setCanonicalizationAlgorithm(c14nAlg);Selecting the signature algorithm
Specify and set the signature algorithm using the following classes.
iaik.ixsil.algorithms.SignatureAlgorithmImplDSAiaik.ixsil.algorithms.SignatureAlgorithmImplRSAiaik.ixsil.algorithms.SignatureAlgorithmInstantiate a signature algorithm of the appropriate kind and set the corresponding URI.
SignatureAlgorithm signatureAlg = null ;PrivateKey privatekey = keySource.getSigningKey();if(privatekey.getAlgorithm().equals("DSA")){ signatureAlg = new SignatureAlgorithmImplDSA(); signatureAlg.setURI(new URI("http://www.w3.org/2000/09/xmldsig#dsa-sha1"));}else{ signatureAlg = new SignatureAlgorithmImplRSA(); signatureAlg.setURI(new URI("http://www.w3.org/2000/09/xmldsig#rsa-sha1"));}Set the private key.
signatureAlg.setSignerKey(privatekey);Set the algorithm.
signedInfo.setSignatureAlgorithm(signatureAlg);Referencing the signed data
Configure references to the resources you want to sign and add them to the <SignedInfo> element.
SignerReference reference = signedInfo.createReference();Set the URI to null so that the enveloped signature is over the entire XML document.
reference.setURI(new URI("") );To sign a particular element of a SOAP message (or any message), instead of signing the entire XML document, use the following and pass in the ID attribute of the element to be signed.
URI uri = new URI(null, null, "", null, id);Create an enveloped signature transform.
TransformImplEnvelopedSignature transform = new TransformImplEnvelopedSignature();Set the transform's algorithm URI.
transform.setURI(new URI("http://www.w3.org/2000/09/xmldsig#enveloped-signature"));Set the enveloped signature transform in reference to prevent the signing operation from signing the <Signature> element itself.
reference.insertTransformAt(transform, 0);Create a digest algorithm.
DigestAlgorithmImplSHA1 digestAlg1 = new DigestAlgorithmImplSHA1();Set the digest algorithm's URI.
digestAlg1.setURI(new URI("http://www.w3.org/2000/09/xmldsig#sha1"));Set the digest algorithm.
reference.setDigestAlgorithm(digestAlg1);Add the resource reference to the signature.
signedInfo.addReference(reference);The <SignedInfo> element contains one or more references to the resources signed by the XML signature. This step configures and adds one reference to the XML signature. To add more references, repeat the step.
Selecting the digest algorithm
Create a new instance of the digest algorithm.
DigestAlgorithmImplSHA1 digestAlg1 = new DigestAlgorithmImplSHA1();Set the URI of the digest algorithm.
digestAlg1.setURI(new URI("http://www.w3.org/2000/09/xmldsig#sha1"));Set the digest algorithm.
firstRef.setDigestAlgorithm(digestAlg1);Add the resource reference to the signature.
signedInfo.addReference(firstRef);Adding key information
Instantiate a key manager.
Document signatureDOMDoc = signer.toDocument();KeyManagerImpl keyManager = new KeyManagerImpl(signatureDOMDoc);Create and configure a KeyInfo provider for the X509Data clause.
KeyProviderImplX509Data keyProviderX509Data = new KeyProviderImplX509Data(signatureDOMDoc);Include the user's verification certificate in the <KeyInfo> element.
X509Certificate certificate = keySource.getVerificationCertificate();X509Data x509 = new X509Data();x509.insertHintAt(certificate, 0) ;Include the user's distinguished name in the <KeyInfo> element.
X509SubjectName x509Name = new X509SubjectName((Name) certificate.getSubjectDN());x509.insertHintAt(x509Name, 0);keyProviderX509Data.insertX509DataAt(x509, 0);Create and configure a KeyInfo provider for the KeyValue clause.
KeyProviderImplKeyValue keyProviderKeyValue = new KeyProviderImplKeyValue(signatureDOMDoc);keyProviderKeyValue.setVerifierKey(certificate.getPublicKey());Add any of these KeyInfo providers.
keyManager.addKeyProvider(keyProviderKeyValue);keyManager.addKeyProvider(keyProviderX509Data);Set the signature's key manager.
signer.getSignature().setKeyManager((SignerKeyManager) keyManager);Adding the KeyInfo element
If your application supports non-repudiation of XML digital signatures, create a reference for the <KeyInfo> element.
SignerReference ref = signedInfo.createReference();Identify the <KeyInfo> element reference with a URI.
String keyInfoId = keyManager.getId();ref.setURI(new URI(null, null, null, null, keyInfoId));Add the <KeyInfo> element reference to the resources to be signed.
signedInfo.addReference(ref);Generating the signature
Calculate the signature value.
signer.getSignature().sign();Return the signed document to complete the procedure.
return signer.toDocument();