上面三章做了通过WSDL文件生成java code的WebService服务器端和客户端例子。下面我们来做通过WSS4J对WebService的加密。
?
1.下载wss4j.jar 还是自己用google去找来下载。
2.把wss4j.jar 放到VacSyncService_WSS4J工程的 /WebContent/WEB-INF/lib 下。 可能提VacSyncService_WSS4J工程有点晕,其实这个就是前面我们使用的VacSyncService工程改了一下名字而已。
3.这下开始配置WEB-INFO 下的 deploy.wsdd
<!-- Use this file to deploy some handlers/chains and services????? -->
<!-- Two ways to do this:?????????????????????????????????????????? -->
<!--?? java org.apache.axis.client.AdminClient deploy.wsdd????????? -->
<!--????? after the axis server is running????????????????????????? -->
<!-- or???????????????????????????????????????????????????????????? -->
<!--?? java org.apache.axis.utils.Admin client|server deploy.wsdd?? -->
<!--????? from the same directory that the Axis engine runs???????? -->
<deployment
??? xmlns="http://xml.apache.org/axis/wsdd/"
??? xmlns:java="http://xml.apache.org/axis/wsdd/providers/java">
? <!-- Services from SyncNotifySPServiceService WSDL service -->
? <service name="SyncNotifySP" provider="java:RPC" style="rpc" use="encoded">
? ?<requestFlow>
?? ??<handler type="java:org.apache.ws.axis.security.WSDoAllReceiver">
??? ?<parameter name="passwordCallbackClass" value="PWCallback"/>
??? ?<parameter name="action" value="UsernameToken"/>
?? ??</handler>
? ?</requestFlow>????
????? <parameter name="wsdlTargetNamespace" value="http://soap.bossagent.vac.unicom.com"/>
????? <parameter name="wsdlServiceElement" value="SyncNotifySPServiceService"/>
????? <parameter name="schemaUnqualified" value="http://rsp.sync.soap.bossagent.vac.unicom.com,http://req.sync.soap.bossagent.vac.unicom.com"/>
????? <parameter name="wsdlServicePort" value="SyncNotifySP"/>
????? <parameter name="className" value="com.unicom.vac.bossagent.soap.SyncNotifySPSoapBindingSkeleton"/>
????? <parameter name="wsdlPortType" value="SyncNotifySPService"/>
????? <parameter name="typeMappingVersion" value="1.2"/>
????? <parameter name="allowedMethods" value="*"/>
????? <parameter name="scope" value="Session"/>
????? <typeMapping
??????? xmlns:ns="http://rsp.sync.soap.bossagent.vac.unicom.com"
??????? qname="ns:OrderRelationUpdateNotifyResponse"
??????? type="java:com.unicom.vac.bossagent.soap.sync.rsp.OrderRelationUpdateNotifyResponse"
??????? serializer="org.apache.axis.encoding.ser.BeanSerializerFactory"
??????? deserializer="org.apache.axis.encoding.ser.BeanDeserializerFactory"
??????? encodingStyle="http://schemas.xmlsoap.org/soap/encoding/"
????? />
????? <typeMapping
??????? xmlns:ns="http://req.sync.soap.bossagent.vac.unicom.com"
??????? qname="ns:OrderRelationUpdateNotifyRequest"
??????? type="java:com.unicom.vac.bossagent.soap.sync.req.OrderRelationUpdateNotifyRequest"
??????? serializer="org.apache.axis.encoding.ser.BeanSerializerFactory"
??????? deserializer="org.apache.axis.encoding.ser.BeanDeserializerFactory"
??????? encodingStyle="http://schemas.xmlsoap.org/soap/encoding/"
????? />
? </service>
</deployment>
红色字体为加入部分。
?
4.我们来写加密的类
import java.io.IOException;
import javax.security.auth.callback.Callback;
import javax.security.auth.callback.CallbackHandler;
import javax.security.auth.callback.UnsupportedCallbackException;
import org.apache.ws.security.WSPasswordCallback;
?
public class PWCallback implements CallbackHandler {
?
?
?public void handle(Callback[] callbacks) throws IOException,
???UnsupportedCallbackException {
???????? for (int i = 0; i < callbacks.length; i++) {
?
???????????? if (callbacks[i] instanceof WSPasswordCallback) {
?
???????????????? WSPasswordCallback pc = (WSPasswordCallback)callbacks[i];
???????????????? // set the password given a username
???????????????? if ("user".equals(pc.getIdentifer())) {
?
???????????????????? pc.setPassword("pawd");
???????????????? }
?
???????????? } else {
?
???????????????? throw new UnsupportedCallbackException(callbacks[i],"Unrecognized Callback");
?
???????????? }
?
???????? }
??}
?
}
?
这个就是服务器端加密类。可以看到用户明就是user,密码就是pawd,这里可以根据自己需要用加密机或算法类处理一下。
?
5.在MyEclipse里面启动Tomcat。打开cmd输入:
C:/apache-tomcat-6.0.32/webapps/VacSyncService_WSS4J/WEB-INF>java -Djava.ext.dir
s="D:/workspace/VacSyncService_WSS4J/WebContent/WEB-INF/lib" org.apache.axis.cli
ent.AdminClient -lhttp://localhost:8080/VacSyncService_WSS4J/services/AdminServi
ce? deploy.wsdd
在 /apache-tomcat-6.0.32/webapps/VacSyncService_WSS4J/WEB-INF/? 下会生成server-config.wsdd
?
6.到目前服务器端加密的用户验证就写完了,我们先用之前的客户端类调用一下这个WebService服务会抛如下错误:
AxisFault
?faultCode: {http://schemas.xmlsoap.org/soap/envelope/}Server.generalException
?faultSubcode:
?faultString: WSHandler: cannot load password callback class: PWCallback; nested exception is:
?java.lang.ClassNotFoundException: PWCallback; nested exception is:
?org.apache.ws.security.WSSecurityException: WSHandler: cannot load password callback class: PWCallback; nested exception is:
?java.lang.ClassNotFoundException: PWCallback
?faultActor:
?faultNode:
?faultDetail:
?{http://xml.apache.org/axis/}hostname:3ABF8BC3B347428
WSHandler: cannot load password callback class: PWCallback; nested exception is:
?java.lang.ClassNotFoundException: PWCallback; nested exception is:
?org.apache.ws.security.WSSecurityException: WSHandler: cannot load password callback class: PWCallback; nested exception is:
?java.lang.ClassNotFoundException: PWCallback
?at org.apache.axis.message.SOAPFaultBuilder.createFault(SOAPFaultBuilder.java:222)
?at org.apache.axis.message.SOAPFaultBuilder.endElement(SOAPFaultBuilder.java:129)
?at org.apache.axis.encoding.DeserializationContext.endElement(DeserializationContext.java:1087)
?at com.sun.org.apache.xerces.internal.parsers.AbstractSAXParser.endElement(AbstractSAXParser.java:601)
?at com.sun.org.apache.xerces.internal.impl.XMLDocumentFragmentScannerImpl.scanEndElement(XMLDocumentFragmentScannerImpl.java:1774)
?at com.sun.org.apache.xerces.internal.impl.XMLDocumentFragmentScannerImpl$FragmentContentDriver.next(XMLDocumentFragmentScannerImpl.java:2930)
?at com.sun.org.apache.xerces.internal.impl.XMLDocumentScannerImpl.next(XMLDocumentScannerImpl.java:648)
?at com.sun.org.apache.xerces.internal.impl.XMLNSDocumentScannerImpl.next(XMLNSDocumentScannerImpl.java:140)
?at com.sun.org.apache.xerces.internal.impl.XMLDocumentFragmentScannerImpl.scanDocument(XMLDocumentFragmentScannerImpl.java:510)
?at com.sun.org.apache.xerces.internal.parsers.XML11Configuration.parse(XML11Configuration.java:807)
?at com.sun.org.apache.xerces.internal.parsers.XML11Configuration.parse(XML11Configuration.java:737)
?at com.sun.org.apache.xerces.internal.parsers.XMLParser.parse(XMLParser.java:107)
?at com.sun.org.apache.xerces.internal.parsers.AbstractSAXParser.parse(AbstractSAXParser.java:1205)
?at com.sun.org.apache.xerces.internal.jaxp.SAXParserImpl$JAXPSAXParser.parse(SAXParserImpl.java:522)
?at javax.xml.parsers.SAXParser.parse(SAXParser.java:395)
?at org.apache.axis.encoding.DeserializationContext.parse(DeserializationContext.java:227)
?at org.apache.axis.SOAPPart.getAsSOAPEnvelope(SOAPPart.java:696)
?at org.apache.axis.Message.getSOAPEnvelope(Message.java:435)
?at org.apache.axis.handlers.soap.MustUnderstandChecker.invoke(MustUnderstandChecker.java:62)
?at org.apache.axis.client.AxisClient.invoke(AxisClient.java:206)
?at org.apache.axis.client.Call.invokeEngine(Call.java:2784)
?at org.apache.axis.client.Call.invoke(Call.java:2767)
?at org.apache.axis.client.Call.invoke(Call.java:2443)
?at org.apache.axis.client.Call.invoke(Call.java:2366)
?at org.apache.axis.client.Call.invoke(Call.java:1812)
?at com.unicom.vac.bossagent.soap.SyncNotifySPSoapBindingStub.orderRelationUpdateNotify(SyncNotifySPSoapBindingStub.java:160)
?at com.unicom.vac.bossagent.soap.WebServiceClient.setRequest(WebServiceClient.java:41)
?at com.unicom.vac.bossagent.soap.WebServiceClient.main(WebServiceClient.java:59)
接下来我们来写客户端验证代码。