CSDN博客

img yuzhouhenan

基于verisign实现wss例子全部类

发表于2008/9/30 10:48:00  590人阅读

这是网上流传的比较广的例子,但没有一个提供完整的类,作者将其空缺的类实现,全部如下:
基于tsik.jar,ISNetworksProvider.jar,ws-security.jar可以到csdn的down下载
package wss;
import org.w3c.dom.Document;
import javax.xml.soap.SOAPMessage;
import javax.xml.transform.TransformerFactory;
import javax.xml.transform.Transformer;
import java.io.*;
import javax.xml.transform.dom.DOMSource;
import javax.xml.soap.MimeHeaders;
import javax.xml.transform.stream.StreamResult;
import javax.xml.soap.MessageFactory;
import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.parsers.DocumentBuilder;
public class MessageConverter {
  public static SOAPMessage convertDocumentToSOAPMessage(Document doc)
    throws Exception {
   TransformerFactory transformerFactory = TransformerFactory
     .newInstance();
   Transformer transformer = transformerFactory.newTransformer();

   ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream();
   transformer.transform(new DOMSource(doc), new StreamResult(
     byteArrayOutputStream));
   MimeHeaders header = new MimeHeaders();
   header.addHeader("Content-Type", "text/xml");
   MessageFactory factory = MessageFactory.newInstance();
   SOAPMessage soapMsg = factory.createMessage(header,
     new ByteArrayInputStream(byteArrayOutputStream.toByteArray(),
       0, byteArrayOutputStream.size()));

   return soapMsg;
  }

  /**
   * SOAPMessage转换成Document
   */
  public static Document convertSoapMessageToDocument(SOAPMessage soapMsg)
    throws Exception {
   ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream();
   soapMsg.writeTo(byteArrayOutputStream);
   ByteArrayInputStream bais = new ByteArrayInputStream(
     byteArrayOutputStream.toByteArray(), 0, byteArrayOutputStream
       .size());

   DocumentBuilderFactory documentBuilderFactory = DocumentBuilderFactory
     .newInstance();
   documentBuilderFactory.setNamespaceAware(true);
   DocumentBuilder documentBuilder = documentBuilderFactory
     .newDocumentBuilder();
   Document doc = documentBuilder.parse(bais);
   return doc;
  }

}
package wss;
import org.apache.axis.handlers.*;
import org.apache.axis.AxisFault;
import org.apache.axis.MessageContext;
public class WSClientHandler extends BasicHandler{
protected String keyStoreFile ;
protected String keyStoreType ="JKS";//默认
protected String keyStorePassword ;
protected String keyAlias ;
protected String keyEntryPassword ;
protected String trustStoreFile ;
protected String trustStoreType = "JKS";//默认
protected String trustStorePassword ;
protected String certAlias ;

public void setInitialization(String keyStoreFile,String keyStoreType,String keyStorePassword,
          String keyAlias,String keyEntryPassword,String trustStoreFile,
          String trustStoreType,String trustStorePassword,String certAlias){
this.keyStoreFile=keyStoreFile;
this.keyStoreType=keyStoreType;
this.keyStorePassword=keyStorePassword;
this.keyAlias=keyAlias;
this.keyEntryPassword=keyEntryPassword;
this.trustStoreFile=trustStoreFile;
this.trustStoreType=trustStoreType;
this.trustStorePassword=trustStorePassword;
this.certAlias=certAlias;
}
public void setInitialization(String keyStoreFile,String keyStorePassword,
          String keyAlias,String keyEntryPassword,String trustStoreFile,
          String trustStorePassword,String certAlias){
this.keyStoreFile=keyStoreFile;
this.keyStorePassword=keyStorePassword;
this.keyAlias=keyAlias;
this.keyEntryPassword=keyEntryPassword;
this.trustStoreFile=trustStoreFile;
this.trustStorePassword=trustStorePassword;
this.certAlias=certAlias;
}
public void invoke(MessageContext messageContext) throws AxisFault {//在这个方法里对XML文档进行处理
  //do nothing now!
}
public void onFault(MessageContext msgContext) {
  System.out.println("处理错误,这里忽略!");
    }
}

package wss;
import org.apache.axis.handlers.*;
import org.apache.axis.AxisFault;
import org.apache.axis.MessageContext;
import org.apache.axis.message.*;
import java.io.*;
import java.security.MessageDigest;
import javax.xml.soap.SOAPEnvelope;
import javax.xml.soap.SOAPMessage;
import javax.xml.soap.SOAPElement;
import org.w3c.dom.Document;
public class WSClientRequestHandler extends WSClientHandler{
public void invoke(MessageContext messageContext) throws AxisFault {
  try {

  SOAPMessage soapMessage = messageContext.getMessage();
  System.out.print("签名加密以前"+soapMessage.getSOAPPart().getEnvelope());
  Document doc = MessageConverter.convertSoapMessageToDocument (soapMessage); //soapMessage转换为Document
  WSHelper.sign (doc, keyStoreFile, keyStoreType,keyStorePassword, keyAlias,  keyEntryPassword); //数字签名
  WSHelper.encrypt(doc, trustStoreFile, trustStoreType, trustStorePassword, certAlias); //加密
  soapMessage = MessageConverter.convertDocumentToSOAPMessage(doc);
  System.out.print("签名加密以后"+soapMessage.getSOAPPart().getEnvelope());
//处理后的Document再转换回soapMessage
  messageContext.setMessage(soapMessage);
  } catch (Exception e){
  System.err.println("在处理响应时发生以下错误: " + e);
    e.printStackTrace(); }
    }
}

package wss;
import org.apache.axis.handlers.*;
import org.apache.axis.AxisFault;
import org.apache.axis.MessageContext;
import org.apache.axis.message.*;
import java.io.*;
import java.security.MessageDigest;
import javax.xml.soap.SOAPEnvelope;
import javax.xml.soap.SOAPMessage;
import javax.xml.soap.SOAPElement;
import org.w3c.dom.Document;

public class WSClientResponseHandler extends WSClientHandler{
public void invoke(MessageContext messageContext) throws AxisFault {
  try {

        SOAPMessage soapMessage = messageContext.getCurrentMessage();
        Document doc = MessageConverter.convertSoapMessageToDocument(soapMessage);

    WSHelper.decrypt(doc, keyStoreFile, keyStoreType,
                    keyStorePassword, keyAlias, keyEntryPassword); //解密

        WSHelper.verify (doc, trustStoreFile, trustStoreType, trustStorePassword); //验证
        WSHelper.removeWSSElements(doc);
        soapMessage = MessageConverter.convertDocumentToSOAPMessage(doc);
        messageContext.setMessage(soapMessage);
  } catch (Exception e){
        e.printStackTrace();
        System.err.println("在处理响应时发生以下错误: " + e);
                }

    }
}

package wss;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import org.w3c.dom.Document;
import java.security.PrivateKey;
import java.security.cert.X509Certificate;

import com.verisign.xmlsig.Signer;
import com.verisign.xmlsig.SigningKey;
import com.verisign.xmlsig.SigningKeyFactory;
import com.verisign.xmlsig.KeyInfo;
import com.verisign.messaging.WSSecurity;
import com.verisign.xpath.XPath;
import org.xmltrustcenter.verifier.X509TrustVerifier;
import org.xmltrustcenter.verifier.TrustVerifier;
import com.verisign.messaging.MessageValidity;
import java.security.PublicKey;
import javax.crypto.KeyGenerator;
import java.security.SecureRandom;
import javax.crypto.SecretKey;
import com.verisign.xmlenc.AlgorithmType;
public class WSHelper {
   static String PROVIDER="ISNetworks";//JSSE安全提供者。
//添加JSSE安全提供者,你也可以使用其它安全提供者。只要支持DESede算法。这是程序里动态加载还可以在JDK中静态加载
   static
   {
     java.security.Security.addProvider(new com.isnetworks.provider.jce.ISNetworksProvider());
 }
 /**
 *对XML文档进行数字签名。
 */
   public static void sign(Document doc, String keystore, String storetype,
                               String storepass, String alias, String keypass) throws Exception {
         FileInputStream fileInputStream = new FileInputStream(keystore);
         java.security.KeyStore keyStore = java.security.KeyStore.getInstance(storetype);
         keyStore.load(fileInputStream, storepass.toCharArray());
         PrivateKey key = (PrivateKey)keyStore.getKey(alias, keypass.toCharArray());
         X509Certificate cert = (X509Certificate)keyStore.getCertificate(alias);
         SigningKey sk = SigningKeyFactory.makeSigningKey(key);
         KeyInfo ki = new KeyInfo();
         ki.setCertificate(cert);
         WSSecurity wss  = new WSSecurity();//ws-security.jar中包含的WSSecurity类
         wss.sign(doc, sk, ki);//签名。
        // com.verisign.xmlsig.Signer s=new com.verisign.xmlsig.Signer(doc, sk, ki);
        // doc=s.sign();


   }
 /**
 *对XML文档进行身份验证。
 */
   public static boolean verify(Document doc, String keystore, String storetype,
                               String storepass) throws Exception {
         FileInputStream fileInputStream = new FileInputStream(keystore);
         java.security.KeyStore keyStore = java.security.KeyStore.getInstance(storetype);
         keyStore.load(fileInputStream, storepass.toCharArray());
         TrustVerifier verifier = new X509TrustVerifier(keyStore);
         WSSecurity wSSecurity = new WSSecurity();
         MessageValidity[] resa = wSSecurity.verify(doc, verifier, null,null);
         if (resa.length > 0)
               return resa[0].isValid();
         return false;
   }
 /**
 *对XML文档进行加密。必须有JSSE提供者才能加密。
 */
   public static void encrypt(Document doc, String keystore, String storetype,
                               String storepass, String alias) throws Exception {
         try
         {
         FileInputStream fileInputStream = new FileInputStream(keystore);
         java.security.KeyStore keyStore = java.security.KeyStore.getInstance(storetype);
         keyStore.load(fileInputStream, storepass.toCharArray());
         X509Certificate cert = (X509Certificate)keyStore.getCertificate(alias);
         PublicKey pubk = cert.getPublicKey();
         KeyGenerator keyGenerator = KeyGenerator.getInstance("DESede",PROVIDER);
         keyGenerator.init(168, new SecureRandom());
         SecretKey key = keyGenerator.generateKey();
         KeyInfo ki = new KeyInfo();
         ki.setCertificate(cert);
         WSSecurity wss = new WSSecurity();
         wss.encrypt(doc, key, AlgorithmType.TRIPLEDES, pubk, AlgorithmType.RSA1_5, ki);
      // com.verisign.xmlenc.Encryptor enc=new  com.verisign.xmlenc.Encryptor(doc, key, AlgorithmType.TRIPLEDES, pubk, AlgorithmType.RSA1_5, ki);
      // doc=enc.encrypt();
     }
   catch(Exception e)
   {
         e.printStackTrace();
   }
   }
 /**
 *对文档进行解密。
 */
   public static void decrypt(Document doc, String keystore, String storetype,
                               String storepass, String alias, String keypass) throws Exception {
          System.out.print(doc);
         FileInputStream fileInputStream = new FileInputStream(keystore);
         java.security.KeyStore keyStore = java.security.KeyStore.getInstance(storetype);
         keyStore.load(fileInputStream, storepass.toCharArray());
         PrivateKey prvk2 = (PrivateKey)keyStore.getKey(alias, keypass.toCharArray());

         WSSecurity wSSecurity = new WSSecurity();
         wSSecurity.decrypt(doc, prvk2, null);
         String xpath = "//xenc:EncryptedData";
         String[] ns ={ "xenc", "http://www.w3.org/2001/04/xmlenc#" };
         XPath xPath = new XPath(xpath, ns);

        // com.verisign.xmlenc.Decryptor dec=new com.verisign.xmlenc.Decryptor(doc, prvk2, xPath);
        // doc=dec.decrypt();
         WSSecurityExtn.removeWSSEncryptedKey (doc);//从 WS-Security Header中删除 EncryptedKey 元素
   }

   public static void removeWSSElements(Document doc) throws Exception {
       WSSecurityExtn.removeWSSInfo(doc);// 删除WSS相关的元素。
   }

}

package wss;


import org.w3c.dom.Document;
import com.verisign.domutil.DOMWriteCursor;
import com.verisign.domutil.DOMCursor;
import com.verisign.messaging.XmlMessageException;
import com.verisign.util.Namespaces;

public class WSSecurityExtn {
    private static final String WSSE_URI =
        "http://schemas.xmlsoap.org/ws/2002/07/secext";
   private static final String WSSE_PREFIX = "wsse";
    private static final String WSU_URI =
       "http://schemas.xmlsoap.org/ws/2002/07/utility";
  private static final String WSU_PREFIX = "wsu";
 private static final String SOAP_URI = Namespaces.SOAPENV.getUri();
   private static final String SOAP_PREFIX = Namespaces.SOAPENV.getPrefix();
   private static final String XMLSIG_URI = Namespaces.XMLSIG.getUri();
   private static final String XMLSIG_PREFIX = Namespaces.XMLSIG.getPrefix();
    private static final String XMLENC_URI = Namespaces.XMLENC.getUri();
    private static final String XMLENC_PREFIX = Namespaces.XMLENC.getPrefix();
   private static final String SOAP_ENVELOPE = "Envelope";
    private static final String SOAP_HEADER = "Header";
    private static final String SOAP_BODY = "Body";
    private static final String SOAP_FAULT = "Fault";
    private static final boolean USE_WSU_FOR_SECURITY_TOKEN_ID = false;

    public static void removeWSSEncryptedKey(Document message) throws XmlMessageException {
        DOMWriteCursor c = new DOMWriteCursor(message);
        checkEnvelope(c);

        // Remove EncryptedKey elem. from WS-Security Header Element
        if (c.moveToChild(SOAP_URI, SOAP_HEADER)) {
            if (c.moveToChild(WSSE_URI, "Security")) {
                if (c.moveToChild(XMLENC_URI, "EncryptedKey")) {
                   c.remove();
                }
            }
        }
    }

    public static void removeWSSInfo(Document message) throws XmlMessageException {
        DOMWriteCursor c = new DOMWriteCursor(message);
        checkEnvelope(c);

        // Remove WS-Security Header Element
        if (c.moveToChild(SOAP_URI, SOAP_HEADER)) {
            if (c.moveToChild(WSSE_URI, "Security")) {
                c.remove();
           }
        }

        // Remove Timestamp Header Element
       c.moveToTop();
        if (c.moveToChild(SOAP_URI, SOAP_HEADER)) {
            if (c.moveToChild(WSU_URI, "Timestamp")) {
                c.remove();
            }
        }

        // Remove wsu:Id attribute from Body Element
        c.moveToTop();
        if (c.moveToChild(SOAP_URI, SOAP_BODY)) {
            c.setAttribute(WSU_URI, WSU_PREFIX, "Id", null);
        }
    }

    private static void checkEnvelope(DOMCursor c) throws XmlMessageException {
        c.moveToTop();
        if (!c.atElement(SOAP_URI, SOAP_ENVELOPE)) {
            throw new XmlMessageException("Missing SOAP envelope");
        }
  }
}
package wss;
import org.apache.axis.handlers.*;
import org.apache.axis.AxisFault;
import org.apache.axis.MessageContext;

public class WSServerHandler extends BasicHandler{
protected St