2013-04-08 113 views
0

我使用wsdl2java成功生成了Java類。現在我正在嘗試構建訪問Web服務的客戶端。我正在使用Apache CXF。 在嘗試連接時,我得到以下錯誤:WS安全錯誤:181001嘗試通過Apache CXF訪問Web服務時

Exception in thread "main" javax.xml.ws.soap.SOAPFaultException: WS Security Error : 181001 
    at org.apache.cxf.jaxws.JaxWsClientProxy.invoke(JaxWsClientProxy.java:155) 
    at $Proxy36.getCustomerOp(Unknown Source) 
    at com.ievgen.webservices.TestClient4.main(TestClient4.java:87) 
Caused by: org.apache.cxf.binding.soap.SoapFault: WS Security Error : 181001 
    at org.apache.cxf.binding.soap.interceptor.Soap11FaultInInterceptor.unmarshalFault(Soap11FaultInInterceptor.java:75) 
    at org.apache.cxf.binding.soap.interceptor.Soap11FaultInInterceptor.handleMessage(Soap11FaultInInterceptor.java:46) 
    at org.apache.cxf.binding.soap.interceptor.Soap11FaultInInterceptor.handleMessage(Soap11FaultInInterceptor.java:35) 
    at org.apache.cxf.phase.PhaseInterceptorChain.doIntercept(PhaseInterceptorChain.java:271) 
    at org.apache.cxf.interceptor.AbstractFaultChainInitiatorObserver.onMessage(AbstractFaultChainInitiatorObserver.java:114) 
    at org.apache.cxf.binding.soap.interceptor.CheckFaultInterceptor.handleMessage(CheckFaultInterceptor.java:69) 
    at org.apache.cxf.binding.soap.interceptor.CheckFaultInterceptor.handleMessage(CheckFaultInterceptor.java:34) 
    at org.apache.cxf.phase.PhaseInterceptorChain.doIntercept(PhaseInterceptorChain.java:271) 
    at org.apache.cxf.endpoint.ClientImpl.onMessage(ClientImpl.java:800) 
    at org.apache.cxf.transport.http.HTTPConduit$WrappedOutputStream.handleResponseInternal(HTTPConduit.java:1592) 
    at org.apache.cxf.transport.http.HTTPConduit$WrappedOutputStream.handleResponse(HTTPConduit.java:1490) 
    at org.apache.cxf.transport.http.HTTPConduit$WrappedOutputStream.close(HTTPConduit.java:1309) 
    at org.apache.cxf.transport.AbstractConduit.close(AbstractConduit.java:56) 
    at org.apache.cxf.transport.http.HTTPConduit.close(HTTPConduit.java:622) 
    at org.apache.cxf.interceptor.MessageSenderInterceptor$MessageSenderEndingInterceptor.handleMessage(MessageSenderInterceptor.java:62) 
    at org.apache.cxf.phase.PhaseInterceptorChain.doIntercept(PhaseInterceptorChain.java:271) 
    at org.apache.cxf.endpoint.ClientImpl.doInvoke(ClientImpl.java:530) 
    at org.apache.cxf.endpoint.ClientImpl.invoke(ClientImpl.java:463) 
    at org.apache.cxf.endpoint.ClientImpl.invoke(ClientImpl.java:366) 
    at org.apache.cxf.endpoint.ClientImpl.invoke(ClientImpl.java:319) 
    at org.apache.cxf.frontend.ClientProxy.invokeSync(ClientProxy.java:96) 
    at org.apache.cxf.jaxws.JaxWsClientProxy.invoke(JaxWsClientProxy.java:133) 
    ... 2 more 

據我已經在網絡上找到,181001錯誤意味着所需的認證塊丟失。然而,在文檔描述我已經配置了用戶名和密碼:http://cxf.apache.org/docs/ws-secureconversation.html

這裏是我的代碼:

package com.ievgen.webservices; 

import java.io.File; 

import javax.net.ssl.*; 
import javax.xml.ws.BindingProvider; 
import java.net.MalformedURLException; 
import java.net.URL; 

import org.apache.cxf.configuration.jsse.TLSClientParameters; 
import org.apache.cxf.endpoint.Client; 
import org.apache.cxf.frontend.ClientProxy; 
import org.apache.cxf.transport.http.HTTPConduit; 

import info.app.catalogservices.schemas.customerquery_1.CustomerQueryType; 
import info.app.catalogservices.services.csscatalogservicesinterface_1_0.CustomerError; 
import info.app.catalogservices.services.csscatalogservicesinterface_1_0.IntfCatalogServicesService; 
import info.app.catalogservices.services.csscatalogservicesinterface_1_0.PortType; 

public class TestClient4 { 

    /** 
    * @param args 
    * @throws MalformedURLException 
    */ 
    public static void main(String[] args) throws MalformedURLException { 
     // Create a trust manager that does not validate certificate chains 
     TrustManager[] trustAllCerts = new TrustManager[] { new X509TrustManager() { 
      public java.security.cert.X509Certificate[] getAcceptedIssuers() { 
       return null; 
      } 

      public void checkClientTrusted(
        java.security.cert.X509Certificate[] certs, String authType) { 
      } 

      public void checkServerTrusted(
        java.security.cert.X509Certificate[] certs, String authType) { 
      } 
     } }; 

     // TODO Auto-generated method stub 
     File wsdlFile = new File("WebContent/CatalogServices-1.1.0.wsdl"); 
     URL wsdlUrl = null; 
     if (wsdlFile.exists()) { 
      wsdlUrl = wsdlFile.toURL(); 
     } else { 
      System.out.println("File doesn't exist"); 
     } 

     System.out.println("WSDL url: " + wsdlUrl); 
     IntfCatalogServicesService service = new IntfCatalogServicesService(
       wsdlUrl); 
     PortType portType = service.getPortTypeEndpoint(); 

     // This will configure the http conduit dynamically 
     Client client = ClientProxy.getClient(portType); 

     client.getRequestContext().put("ws-security.username", "username"); 
     client.getRequestContext().put("ws-security.password", "password"); 

     HTTPConduit http = (HTTPConduit) client.getConduit(); 

     TLSClientParameters tlsParams = new TLSClientParameters(); 
     // set trust manager which trusts to all certificates 
     tlsParams.setTrustManagers(trustAllCerts); 
     // The certificate provides another CN that it really is, so disable 
     // CNcheck 
     tlsParams.setDisableCNCheck(true); 

     http.setTlsClientParameters(tlsParams); 

     String resp; 
     CustomerQueryType customerQuery = new CustomerQueryType(); 
     customerQuery.setCustomer("0056712120"); 
     java.util.Map<String,Object> requestContext = ((BindingProvider) portType) 
       .getRequestContext(); 
      //I set username/password twice because I am not sure where to do it better 
      //I have found different directions in different sources 
     requestContext.put("ws-security.username", "username"); 
     requestContext.put("ws-security.password", "password"); 
     requestContext 
       .put(BindingProvider.ENDPOINT_ADDRESS_PROPERTY, 
         "https://host:port/Services/intfCatalogServices-service.serviceagent/portTypeEndpoint"); 

     try { 
      resp = portType.getCustomerOp(customerQuery).toString(); 
      System.out.println(resp); 
     } catch (CustomerError e) { 
      e.printStackTrace(); 
     } 
    } 

} 

注:我能使用SOAP UI來訪問Web服務。

你能告訴我我在這裏錯過了什麼嗎?

編輯: 這裏:http://cxf.apache.org/docs/ws-secureconversation.html據說這是neccessary設置「WS-security.username.sct:。在另一方面,在這裏:http://cxf.apache.org/docs/ws-securitypolicy.html據說設置‘WS-security.username’我。已經嘗試了兩種變體,但它們都不適用於我。

回答

1

您正在使用的WSDL是否具有描述安全性需求的WS-Policy片段?如果不是,則WS-SecurityPolicy屬性不會不適用,因爲實際上的策略沒有提及與安全有關的任何事情。

如果沒有任何安全相關策略,則需要手動配置WSS 4J攔截器。請參閱http://cxf.apache.org/docs/ws-security.html

+0

謝謝您的迴應!我已經通過WSDL查看字符串「secur」,並且沒有這樣的字符串。所以我想,我將不得不配置WSS4J攔截器。我應該更徹底地閱讀文檔。 – Ievgen 2013-04-08 20:27:35

+0

丹尼爾,你是對的,我只需要配置出站WSS4J攔截器,它的工作!非常感謝您的幫助。 – Ievgen 2013-04-12 05:37:20

相關問題