客户端在调用受保护的Web服务时出错

时间:2013-04-29 13:03:25

标签: axis2 wso2 wso2esb rampart

我编写了一个调用webservice的客户端。我的客户是:

String publisherEPR = "https://abc:8280/services/ProviderPublication";
        protected void publicationOpenSession(HttpServletRequest request, HttpServletResponse response)
                    throws ServletException, IOException {

                System.out.println("Inside publicationOpenSession");
                date = new Date();
                namespace = "http://www.openoandm.org/xml/ISBM/";
                fac = OMAbstractFactory.getOMFactory();
                OMNamespace ns = fac.createOMNamespace(namespace, "ns1");

                OMElement result = null;
                channelURI = request.getParameter("TxtPublisher1ChannelURI");
                textfield = request.getParameter("TxtAreaServicePublisherLog");
                String finalChannelURI = "";
                int count = 0;
                try {
                    if (channelURI != null && (channelURI.indexOf(".") > -1)) {
                        System.out.println("Inside If Checking Channel URI");
                        String[] tempChannelURI = channelURI.split("\\.");
                        for (count = 0; count < tempChannelURI.length - 1; count++) {
                            finalChannelURI = finalChannelURI + tempChannelURI[count];
                            if (count < tempChannelURI.length - 2) {
                                finalChannelURI = finalChannelURI + ".";
                            }
                        }
                        System.out.println("Inside If Checking Channel URI : " + finalChannelURI);
                    }
                    System.out.println("OpenPublicationSession" + finalChannelURI);
                    System.out.println(publisherEPR);
                    OMElement OpenPublicationSessionElement = fac.createOMElement("OpenPublicationSession", ns);
                    OMElement ChannelURIElement = fac.createOMElement("ChannelURI", ns);
                    ChannelURIElement.setText(finalChannelURI);
                    OpenPublicationSessionElement.addChild(ChannelURIElement);

                    String webinfFolder = request.getSession().getServletContext().getRealPath("/WEB-INF");
                    ConfigurationContext ctx = ConfigurationContextFactory.createConfigurationContextFromFileSystem(
                            webinfFolder, webinfFolder + "/conf/axis2.xml");

                    Options options = new Options();
                    ServiceClient client = new ServiceClient(ctx, null);
                    EndpointReference targetEPR = new EndpointReference(publisherEPR);
                    options.setTo(targetEPR);
                    options.setAction("urn:OpenPublicationSession");
                    options.setManageSession(true);
                    options.setUserName(user_name);                 
                    java.util.Map<String, Object> m = new java.util.HashMap<String, Object>();
                    /*m.put("javax.net.ssl.trustStorePassword", "wso2carbon");
                    m.put("javax.net.ssl.trustStore", "wso2carbon.jks");
                    */

                    System.out.println(new Date() + " Checkpoint1");
                    // We are accessing STS over HTTPS - so need to set trustStore parameters.
                    System.setProperty("javax.net.ssl.trustStore", "client.jks");
                    System.setProperty("javax.net.ssl.trustStorePassword", "apache");
                    /*m.put("javax.net.ssl.trustStore", "client.jks");
                    m.put("javax.net.ssl.trustStorePassword", "apache");*/
                    /*m.put("org.apache.ws.security.crypto.provider","org.apache.ws.security.components.crypto.Merlin");
                    m.put("org.apache.ws.security.crypto.merlin.keystore.type", "jks");
                    m.put("org.apache.ws.security.crypto.merlin.keystore.password","apache");
                    m.put("org.apache.ws.security.crypto.merlin.file", "client.jks");*/
                    //options.setProperties(m);
                    System.out.println(new Date() + " Checkpoint2");

                    client.setOptions(options);

                    MessageContext messageContext = new MessageContext();
                    messageContext.setOptions(options);
                    messageContext.setMessageID("MyMessageID");
                    System.out.println("provider:user_name: " + user_name);
                    messageContext.setProperty("username", user_name);
                    messageContext.setProperty("password", user_password);
                    MessageContext.setCurrentMessageContext(messageContext);
                    messageContext.setProperty("myproperty", "mypropertyvalue");

                    String falconNS = "http://cts.falcon.isbm";
                    falcon = fac.createOMNamespace(falconNS, "falcon");
                    OMElement falconUserElement = fac.createOMElement("FalconUser", falcon);
                    falconUserElement.setText(user_name);
                    client.addHeader(falconUserElement);

                    // invoke web-service
                    try {
                        errorText = "Client Didnt Respond.";

                        result = client.sendReceive(OpenPublicationSessionElement);
                        System.out.println(result.toString());
                        OMElement SessionIDElement = null;
                        SessionIDElement = result.getFirstChildWithName(new QName(namespace, "SessionID"));
                        SessionID = SessionIDElement.getText();

                        request.setAttribute("PublisherSession", SessionID);

                        StringBuffer text = new StringBuffer();
                        text.append((request.getParameter("TxtAreaServicePublisherLog")).trim());
                        text.trimToSize();

                        SessionID = SessionIDElement.getText();

                        StringBuffer publisherLog = new StringBuffer();
                        publisherLog.append((request.getParameter("TxtAreaServicePublisherLog")).trim());

                        publisherLog.trimToSize();
                        System.out.println("Checkpoint1");

                        publisherLog.append("\n" + new Date().toString() + " " + PUBLISHER_SESSION_SUCCESS_MSG + SessionID);

                        request.setAttribute("textMessageService2", publisherLog);
                        request.setAttribute("PublisherSession", SessionID);
                        System.out.println("Checkpoint3");

                        RequestDispatcher rd = request.getRequestDispatcher("/Provider.jsp");// hard-coded

                        try {
                            rd.forward(request, response);
                        } catch (IOException ioe) {
                            ioe.printStackTrace();
                        } catch (ServletException se) {
                            se.printStackTrace();
                        }

                    } catch (Exception e) {

                        errorText = "Client not responding";
                        buildErrorLog(request, response, e);
                        e.printStackTrace();
                    }

                    //buildCallLog(request, response, result);

                } catch (Exception e) {
                    e.printStackTrace();
                    buildErrorLog(request, response, e);
                }
            }

And i have a proxy service upon which i have implemented security and its url is:

https://abc:8280/services/ProviderPublication.

我在回调处理程序中的句柄方法是:

public void handle(Callback[] callbacks) throws IOException, UnsupportedCallbackException {
        System.out.println("\n \n " + new Date() + " ISBMClient.PWCBHandler.handle");
        if(MessageContext.getCurrentMessageContext() == null){
            System.out.println("CurrentMessageContext is null");                
        }else{
            //get the credentials from the jsp
            System.out.println("MessageID: " + MessageContext.getCurrentMessageContext().getMessageID());
            dynamicUser = MessageContext.getCurrentMessageContext().getProperty("username").toString();
            dynamicPassword = MessageContext.getCurrentMessageContext().getProperty("password").toString();
            System.out.println("MessageContext user_name: " + dynamicUser);
            System.out.println("MessageContext user_password: " + dynamicPassword);         
        }
        for (int i = 0; i < callbacks.length; i++) {
            WSPasswordCallback pwcb = (WSPasswordCallback)callbacks[i];
            pwcb.setIdentifier(dynamicUser);
            String id = pwcb.getIdentifier();
            System.out.println("Invoking service with user: " + id);
            if(dynamicUser.equals(id)){
                pwcb.setPassword(dynamicPassword);
            }
        }
    }

现在的问题是,当我通过我的客户端代码调用此代理服务时,我将获得异常

[INFO] Unable to sendViaPost to url[https://abc:8280/services/ProviderPublication]
org.apache.axis2.AxisFault: Trying to write END_DOCUMENT when document has no root (ie. trying to output empty document).
    at org.apache.axis2.AxisFault.makeFault(AxisFault.java:430)
    at org.apache.axis2.transport.http.SOAPMessageFormatter.writeTo(SOAPMessageFormatter.java:78)
    at org.apache.axis2.transport.http.AxisRequestEntity.writeRequest(AxisRequestEntity.java:84)
    at org.apache.commons.httpclient.methods.EntityEnclosingMethod.writeRequestBody(EntityEnclosingMethod.java:499)
    at org.apache.commons.httpclient.HttpMethodBase.writeRequest(HttpMethodBase.java:2114)
    at org.apache.commons.httpclient.HttpMethodBase.execute(HttpMethodBase.java:1096)
    at org.apache.commons.httpclient.HttpMethodDirector.executeWithRetry(HttpMethodDirector.java:398)
    at org.apache.commons.httpclient.HttpMethodDirector.executeMethod(HttpMethodDirector.java:171)
    at org.apache.commons.httpclient.HttpClient.executeMethod(HttpClient.java:397)
    at org.apache.axis2.transport.http.AbstractHTTPSender.executeMethod(AbstractHTTPSender.java:621)
    at org.apache.axis2.transport.http.HTTPSender.sendViaPost(HTTPSender.java:193)
    at org.apache.axis2.transport.http.HTTPSender.send(HTTPSender.java:75)
    at org.apache.axis2.transport.http.CommonsHTTPTransportSender.writeMessageWithCommons(CommonsHTTPTransportSender.java:404)
    at org.apache.axis2.transport.http.CommonsHTTPTransportSender.invoke(CommonsHTTPTransportSender.java:231)
    at org.apache.axis2.engine.AxisEngine.send(AxisEngine.java:443)
    at org.apache.axis2.description.OutInAxisOperationClient.send(OutInAxisOperation.java:406)
    at org.apache.axis2.description.OutInAxisOperationClient.executeImpl(OutInAxisOperation.java:229)
    at org.apache.axis2.client.OperationClient.execute(OperationClient.java:165)
    at org.apache.axis2.client.ServiceClient.sendReceive(ServiceClient.java:555)
    at org.apache.axis2.client.ServiceClient.sendReceive(ServiceClient.java:531)
    at cts.falcon.isbm.client.Provider.publicationOpenSession(Provider.java:557)
    at cts.falcon.isbm.client.Provider.doPost(Provider.java:852)
    at javax.servlet.http.HttpServlet.service(HttpServlet.java:641)
    at javax.servlet.http.HttpServlet.service(HttpServlet.java:722)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:305)
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:210)
    at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:225)
    at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:123)
    at org.apache.catalina.authenticator.AuthenticatorBase.invoke(AuthenticatorBase.java:472)
    at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:168)
    at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:98)
    at org.apache.catalina.valves.AccessLogValve.invoke(AccessLogValve.java:927)
    at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:118)
    at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:407)
    at org.apache.coyote.http11.AbstractHttp11Processor.process(AbstractHttp11Processor.java:1001)
    at org.apache.coyote.AbstractProtocol$AbstractConnectionHandler.process(AbstractProtocol.java:585)
    at org.apache.tomcat.util.net.JIoEndpoint$SocketProcessor.run(JIoEndpoint.java:310)
    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1110)
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:603)
    at java.lang.Thread.run(Thread.java:722)
Caused by: javax.xml.stream.XMLStreamException: Trying to write END_DOCUMENT when document has no root (ie. trying to output empty document).
    at com.ctc.wstx.sw.BaseStreamWriter.throwOutputError(BaseStreamWriter.java:1473)
    at com.ctc.wstx.sw.BaseStreamWriter.reportNwfStructure(BaseStreamWriter.java:1502)
    at com.ctc.wstx.sw.BaseStreamWriter.finishDocument(BaseStreamWriter.java:1663)
    at com.ctc.wstx.sw.BaseStreamWriter.close(BaseStreamWriter.java:288)
    at org.apache.axiom.util.stax.wrapper.XMLStreamWriterWrapper.close(XMLStreamWriterWrapper.java:46)
    at org.apache.axiom.om.impl.MTOMXMLStreamWriter.close(MTOMXMLStreamWriter.java:222)
    at org.apache.axiom.om.impl.llom.OMSerializableImpl.serializeAndConsume(OMSerializableImpl.java:192)
    at org.apache.axis2.transport.http.SOAPMessageFormatter.writeTo(SOAPMessageFormatter.java:74)
    ... 38 more

但是同样的代码正在为另一个用eclipse编写的Web服务工作。我究竟做错了什么?期待您的回答。提前致谢

2 个答案:

答案 0 :(得分:0)

您需要设置SOAP信封以及从Service Client传输有效负载的SOAP主体。我认为导致这个问题。请参阅此博客文章并重构您的代码以添加它。 http://amilachinthaka.blogspot.com/2009/09/sending-arbitrary-soap-message-with.html

答案 1 :(得分:0)

这里的响应有点晚了,但我遇到了同样的错误消息,经过进一步的挖掘后,由于一些SSL证书失败。

有两种方法可以解决这个问题:

  • 使用keytool命令将可信证书添加到Java。

OR

  • 使用您自己的自定义代码接受所有证书(例如下面的acceptallCerts()方法)

    public class SslUtil {
    
    private static class SmacsTrustManager implements X509TrustManager {
    
        @Override
        public void checkClientTrusted(X509Certificate[] arg0, String arg1) throws CertificateException {}
    
        @Override
        public void checkServerTrusted(X509Certificate[] arg0, String arg1) throws CertificateException {}
    
        @Override
        public X509Certificate[] getAcceptedIssuers() {
            return null;
        }
    }
    
    
    public static void acceptAllCerts(){
        try{
            SSLContext ctx = SSLContext.getInstance("TLS");
            ctx.init(new KeyManager[0], new TrustManager[] {new SmacsTrustManager()}, new SecureRandom());
            SSLContext.setDefault(ctx);
    
        }catch (Exception e){
    
        }
      }
    }