You are viewing a plain text version of this content. The canonical link for it is here.
Posted to java-dev@axis.apache.org by ng...@apache.org on 2008/01/23 22:54:08 UTC

svn commit: r614697 - in /webservices/axis2/trunk/java/modules/jaxws: src/org/apache/axis2/jaxws/client/dispatch/ src/org/apache/axis2/jaxws/client/proxy/ src/org/apache/axis2/jaxws/core/controller/ src/org/apache/axis2/jaxws/core/controller/impl/ src/...

Author: ngallardo
Date: Wed Jan 23 13:54:02 2008
New Revision: 614697

URL: http://svn.apache.org/viewvc?rev=614697&view=rev
Log:
Making the InvocationController pluggable.

Added:
    webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/core/controller/InvocationControllerFactory.java
    webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/core/controller/impl/
    webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/core/controller/impl/AxisInvocationController.java
      - copied, changed from r614254, webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/core/controller/AxisInvocationController.java
    webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/core/controller/impl/InvocationControllerFactoryImpl.java
    webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/core/controller/impl/InvocationControllerImpl.java
    webservices/axis2/trunk/java/modules/jaxws/test/org/apache/axis2/jaxws/client/dispatch/
    webservices/axis2/trunk/java/modules/jaxws/test/org/apache/axis2/jaxws/client/dispatch/InvocationControllerTest.java
Removed:
    webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/core/controller/AxisInvocationController.java
Modified:
    webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/client/dispatch/BaseDispatch.java
    webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/client/proxy/JAXWSProxyHandler.java
    webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/core/controller/InvocationController.java
    webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/registry/FactoryRegistry.java

Modified: webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/client/dispatch/BaseDispatch.java
URL: http://svn.apache.org/viewvc/webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/client/dispatch/BaseDispatch.java?rev=614697&r1=614696&r2=614697&view=diff
==============================================================================
--- webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/client/dispatch/BaseDispatch.java (original)
+++ webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/client/dispatch/BaseDispatch.java Wed Jan 23 13:54:02 2008
@@ -45,14 +45,15 @@
 import org.apache.axis2.jaxws.core.InvocationContext;
 import org.apache.axis2.jaxws.core.InvocationContextFactory;
 import org.apache.axis2.jaxws.core.MessageContext;
-import org.apache.axis2.jaxws.core.controller.AxisInvocationController;
 import org.apache.axis2.jaxws.core.controller.InvocationController;
+import org.apache.axis2.jaxws.core.controller.InvocationControllerFactory;
 import org.apache.axis2.jaxws.description.EndpointDescription;
 import org.apache.axis2.jaxws.i18n.Messages;
 import org.apache.axis2.jaxws.marshaller.impl.alt.MethodMarshallerUtils;
 import org.apache.axis2.jaxws.message.Message;
 import org.apache.axis2.jaxws.message.Protocol;
 import org.apache.axis2.jaxws.message.util.XMLFaultUtils;
+import org.apache.axis2.jaxws.registry.FactoryRegistry;
 import org.apache.axis2.jaxws.spi.Constants;
 import org.apache.axis2.jaxws.spi.ServiceDelegate;
 import org.apache.axis2.jaxws.spi.migrator.ApplicationContextMigratorUtil;
@@ -74,7 +75,8 @@
     protected BaseDispatch(ServiceDelegate svcDelgate, EndpointDescription epDesc) {
         super(svcDelgate, epDesc);
 
-        ic = new AxisInvocationController();
+        InvocationControllerFactory icf = (InvocationControllerFactory) FactoryRegistry.getFactory(InvocationControllerFactory.class);
+        ic = icf.getInvocationController();
     }
 
     /**

Modified: webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/client/proxy/JAXWSProxyHandler.java
URL: http://svn.apache.org/viewvc/webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/client/proxy/JAXWSProxyHandler.java?rev=614697&r1=614696&r2=614697&view=diff
==============================================================================
--- webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/client/proxy/JAXWSProxyHandler.java (original)
+++ webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/client/proxy/JAXWSProxyHandler.java Wed Jan 23 13:54:02 2008
@@ -25,8 +25,8 @@
 import org.apache.axis2.jaxws.core.InvocationContext;
 import org.apache.axis2.jaxws.core.InvocationContextFactory;
 import org.apache.axis2.jaxws.core.MessageContext;
-import org.apache.axis2.jaxws.core.controller.AxisInvocationController;
 import org.apache.axis2.jaxws.core.controller.InvocationController;
+import org.apache.axis2.jaxws.core.controller.impl.AxisInvocationController;
 import org.apache.axis2.jaxws.description.EndpointDescription;
 import org.apache.axis2.jaxws.description.OperationDescription;
 import org.apache.axis2.jaxws.description.ServiceDescription;

Modified: webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/core/controller/InvocationController.java
URL: http://svn.apache.org/viewvc/webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/core/controller/InvocationController.java?rev=614697&r1=614696&r2=614697&view=diff
==============================================================================
--- webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/core/controller/InvocationController.java (original)
+++ webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/core/controller/InvocationController.java Wed Jan 23 13:54:02 2008
@@ -18,29 +18,18 @@
  */
 package org.apache.axis2.jaxws.core.controller;
 
-import org.apache.axis2.jaxws.ExceptionFactory;
 import org.apache.axis2.jaxws.core.InvocationContext;
-import org.apache.axis2.jaxws.core.MessageContext;
-import org.apache.axis2.jaxws.core.util.MessageContextUtils;
-import org.apache.axis2.jaxws.handler.AttachmentsAdapter;
-import org.apache.axis2.jaxws.handler.HandlerChainProcessor;
-import org.apache.axis2.jaxws.handler.HandlerInvokerUtils;
-import org.apache.axis2.jaxws.handler.TransportHeadersAdapter;
-import org.apache.axis2.jaxws.i18n.Messages;
-import org.apache.axis2.jaxws.util.Constants;
-import org.apache.commons.logging.Log;
-import org.apache.commons.logging.LogFactory;
 
 import javax.xml.ws.AsyncHandler;
 import javax.xml.ws.Response;
 
-import java.util.concurrent.ExecutorService;
 import java.util.concurrent.Future;
 
 /**
- * The <tt>InvocationController</tt> is an abstract implementation modeling the invocation of a
- * target web service.  All of the information that the InvocationController needs should exist
- * within the InvocatonContext that is passed in to the various invoke methods.
+ * The <tt>InvocationController</tt> is an interface modeling the invocation of a
+ * target web service.  All of the information that the InvocationController needs 
+ * should exist within the InvocatonContext that is passed in to the various invoke 
+ * methods.
  * <p/>
  * The request information is passed in within the InvocationContext.  The InvocationController
  * assumes that there is a MessageContext within that InvocationContext that is populated with all
@@ -61,9 +50,7 @@
  * <p/>
  * 4) asynchronous (polling) - {@link #invokeAsync(InvocationContext)}
  */
-public abstract class InvocationController {
-
-    private static final Log log = LogFactory.getLog(InvocationController.class);
+public interface InvocationController {
 
     /**
      * Performs a synchronous (blocking) invocation of a target service.  The InvocationContext
@@ -74,77 +61,7 @@
      * @param ic
      * @return
      */
-    public InvocationContext invoke(InvocationContext ic) {
-        if (log.isDebugEnabled()) {
-            log.debug("Invocation pattern: synchronous");
-        }
-
-        // Check to make sure we at least have a valid InvocationContext
-        // and request MessageContext
-        if (ic == null) {
-            throw ExceptionFactory.makeWebServiceException(Messages.getMessage("ICErr1"));
-        }
-        if (ic.getRequestMessageContext() == null) {
-            throw ExceptionFactory.makeWebServiceException(Messages.getMessage("ICErr2"));
-        }
-
-        MessageContext request = ic.getRequestMessageContext();
-        MessageContext response = null;
-
-        request.setProperty(Constants.INVOCATION_PATTERN, InvocationPattern.SYNC);
-
-        // Invoke outbound handlers.
-        boolean success =
-                HandlerInvokerUtils.invokeOutboundHandlers(request.getMEPContext(),
-                                                           ic.getHandlers(),
-                                                           HandlerChainProcessor.MEP.REQUEST,
-                                                           false);
-
-        if (success) {
-            prepareRequest(request);
-            response = doInvoke(request);
-            prepareResponse(response);
-            
-            // make sure request and response contexts share a single parent
-            response.setMEPContext(request.getMEPContext());
-
-            /*
-             * TODO TODO TODO review
-             * 
-             * In most cases we are adding the endpointDesc to the
-             * MessageContext. Notice here that the "response" object is set by
-             * the call to doInvoke. It's a new context we are now working with.
-             * The invokeInboundHandlers uses that context way down in
-             * createMessageContext --> ContextUtils.addProperties()
-             * 
-             * This may also occur in the AsyncResponse class when calling
-             * invokeInboundHandlers
-             * 
-             * For now, make sure the endpointDesc is set on the response
-             * context.
-             */
-            response.setEndpointDescription(request.getEndpointDescription());
-
-            // Invoke inbound handlers.
-            TransportHeadersAdapter.install(response);
-            AttachmentsAdapter.install(response);
-            HandlerInvokerUtils.invokeInboundHandlers(response.getMEPContext(),
-                                                      ic.getHandlers(),
-                                                      HandlerChainProcessor.MEP.RESPONSE,
-                                                      false);
-        } else { // the outbound handler chain must have had a problem, and
-                    // we've reversed directions
-            response = MessageContextUtils.createMinimalResponseMessageContext(request);
-            // since we've reversed directions, the message has "become a
-            // make sure request and response contexts share a single parent
-            response.setMEPContext(request.getMEPContext());
-            response.setMessage(request.getMessage());
-        }
-        ic.setResponseMessageContext(response);
-        return ic;
-    }
-
-    protected abstract MessageContext doInvoke(MessageContext request);
+    public InvocationContext invoke(InvocationContext ic);
 
     /**
      * Performs a one-way invocation of the client.  This is SHOULD NOT be a robust invocation, so
@@ -154,45 +71,7 @@
      *
      * @param ic
      */
-    public void invokeOneWay(InvocationContext ic) throws Exception {
-        if (log.isDebugEnabled()) {
-            log.debug("Invocation pattern: one-way");
-        }
-
-        // Check to make sure we at least have a valid InvocationContext
-        // and request MessageContext
-        if (ic == null) {
-            throw ExceptionFactory.makeWebServiceException("ICErr1");
-        }
-        if (ic.getRequestMessageContext() == null) {
-            throw ExceptionFactory.makeWebServiceException("ICErr2");
-        }
-
-        MessageContext request = ic.getRequestMessageContext();
-        request.setProperty(Constants.INVOCATION_PATTERN, InvocationPattern.ONEWAY);
-
-        // Invoke outbound handlers.
-        boolean success =
-                HandlerInvokerUtils.invokeOutboundHandlers(request.getMEPContext(),
-                                                           ic.getHandlers(),
-                                                           HandlerChainProcessor.MEP.REQUEST,
-                                                           true);
-
-        if (success) {
-            prepareRequest(request);
-            doInvokeOneWay(request);
-        } else { // the outbound handler chain must have had a problem, and we've reversed directions
-            // check to see if problem is due to a handler throwing an exception.  If so, throw it,
-            // even in this oneWay invoke.
-            Exception e = request.getCausedByException();
-            if (e != null) {
-                throw (Exception)e.getCause();
-            }
-        }
-        return;
-    }
-
-    protected abstract void doInvokeOneWay(MessageContext mc);
+    public void invokeOneWay(InvocationContext ic) throws Exception;
 
     /**
      * Performs an asynchronous (non-blocking) invocation of the client based on a callback model.
@@ -203,50 +82,7 @@
      * @param callback
      * @return
      */
-    public Response invokeAsync(InvocationContext ic) {
-        if (log.isDebugEnabled()) {
-            log.debug("Invocation pattern: asynchronous(polling)");
-        }
-
-        // Check to make sure we at least have a valid InvocationContext
-        // and request MessageContext
-        if (ic == null) {
-            throw ExceptionFactory.makeWebServiceException(Messages.getMessage("ICErr1"));
-        }
-        if (ic.getRequestMessageContext() == null) {
-            throw ExceptionFactory.makeWebServiceException(Messages.getMessage("ICErr2"));
-        }
-
-        MessageContext request = ic.getRequestMessageContext();
-        request.setProperty(Constants.INVOCATION_PATTERN, InvocationPattern.ASYNC_POLLING);
-
-        Response resp = null;
-
-        // Invoke outbound handlers.
-        // TODO uncomment, and get the EndpointDescription from the request context, which should soon be available
-        boolean success =
-                HandlerInvokerUtils.invokeOutboundHandlers(request.getMEPContext(),
-                                                           ic.getHandlers(),
-                                                           HandlerChainProcessor.MEP.REQUEST,
-                                                           false);
-        if (success) {
-            prepareRequest(request);
-            resp = doInvokeAsync(request);
-        } else
-        { // the outbound handler chain must have had a problem, and we've reversed directions
-            // since we've reversed directions, the message has "become a response message" (section 9.3.2.1, footnote superscript 2)
-
-            // TODO we know the message is a fault message, we should
-            // convert it to an exception and throw it.
-            // something like:
-
-            //throw new AxisFault(request.getMessage());
-        }
-
-        return resp;
-    }
-
-    public abstract Response doInvokeAsync(MessageContext mc);
+    public Response invokeAsync(InvocationContext ic);
 
     /**
      * Performs an asynchronous (non-blocking) invocation of the client based on a polling model.
@@ -256,82 +92,6 @@
      * @param ic
      * @return
      */
-    public Future<?> invokeAsync(InvocationContext ic, AsyncHandler asyncHandler) {
-        if (log.isDebugEnabled()) {
-            log.debug("Invocation pattern: asynchronous(callback)");
-        }
-
-        // Check to make sure we at least have a valid InvocationContext
-        // and request MessageContext
-        if (ic == null) {
-            throw ExceptionFactory.makeWebServiceException(Messages.getMessage("ICErr1"));
-        }
-        if (ic.getRequestMessageContext() == null) {
-            throw ExceptionFactory.makeWebServiceException(Messages.getMessage("ICErr2"));
-        }
-        if ((ic.getExecutor() != null) && (ic.getExecutor() instanceof ExecutorService)) {
-            ExecutorService es = (ExecutorService) ic.getExecutor();
-            if (es.isShutdown()) {
-                // the executor service is shutdown and won't accept new tasks
-                // so return an error back to the client
-                throw ExceptionFactory.makeWebServiceException(Messages
-                                .getMessage("ExecutorShutdown"));
-            }
-        }
-
-        MessageContext request = ic.getRequestMessageContext();
-        request.setProperty(Constants.INVOCATION_PATTERN, InvocationPattern.ASYNC_CALLBACK);
-
-        Future<?> future = null;
-
-        // Invoke outbound handlers.
-        boolean success =
-                HandlerInvokerUtils.invokeOutboundHandlers(request.getMEPContext(),
-                                                           ic.getHandlers(),
-                                                           HandlerChainProcessor.MEP.REQUEST,
-                                                           false);
-        if (success) {
-            prepareRequest(request);
-            future = doInvokeAsync(request, asyncHandler);
-        } else { // the outbound handler chain must have had a problem, and
-                    // we've reversed directions
-            // since we've reversed directions, the message has "become a
-            // response message" (section 9.3.2.1, footnote superscript 2)
-
-            // TODO: how do we deal with this? The response message may or may
-            // not be a fault
-            // message. We do know that the direction has reversed, so somehow
-            // we need to
-            // flow immediately out of the async and give the exception and/or
-            // response object
-            // back to the client app without calling
-            // AsyncResponse.processResponse or processFault
-        	
-            throw ExceptionFactory.makeWebServiceException(Messages.getMessage("invokeAsyncErr"));
-
-            // throw new AxisFault(request.getMessage());
-        }
-        return future;
-    }
-
-    public abstract Future<?> doInvokeAsync(MessageContext mc, AsyncHandler asyncHandler);
-
-    /**
-     * Abstract method that must be implemented by whoever is providing the specific client binding.
-     *  Once this is called, everything that is needed to invoke the operation must be available in
-     * the MessageContext.
-     *
-     * @param mc
-     */
-    protected abstract void prepareRequest(MessageContext mc);
-
-    /**
-     * Abstract method that must be implemented by whoever is providing the specific client binding.
-     *  This is called after the response has come back and allows the client binding to put
-     * whatever info it has in the response MessageContext.
-     *
-     * @param mc
-     */
-    protected abstract void prepareResponse(MessageContext mc);
+    public Future<?> invokeAsync(InvocationContext ic, AsyncHandler asyncHandler);
 
 }

Added: webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/core/controller/InvocationControllerFactory.java
URL: http://svn.apache.org/viewvc/webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/core/controller/InvocationControllerFactory.java?rev=614697&view=auto
==============================================================================
--- webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/core/controller/InvocationControllerFactory.java (added)
+++ webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/core/controller/InvocationControllerFactory.java Wed Jan 23 13:54:02 2008
@@ -0,0 +1,31 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.axis2.jaxws.core.controller;
+
+public interface InvocationControllerFactory {
+
+    /**
+     * Used to obtain an instance of the InvocationController currently
+     * configured for the runtime.
+     * 
+     * @return A valid InvocationController instance.
+     */
+    public InvocationController getInvocationController();
+    
+}

Copied: webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/core/controller/impl/AxisInvocationController.java (from r614254, webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/core/controller/AxisInvocationController.java)
URL: http://svn.apache.org/viewvc/webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/core/controller/impl/AxisInvocationController.java?p2=webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/core/controller/impl/AxisInvocationController.java&p1=webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/core/controller/AxisInvocationController.java&r1=614254&r2=614697&rev=614697&view=diff
==============================================================================
--- webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/core/controller/AxisInvocationController.java (original)
+++ webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/core/controller/impl/AxisInvocationController.java Wed Jan 23 13:54:02 2008
@@ -16,7 +16,7 @@
  * specific language governing permissions and limitations
  * under the License.
  */
-package org.apache.axis2.jaxws.core.controller;
+package org.apache.axis2.jaxws.core.controller.impl;
 
 import org.apache.axis2.AxisFault;
 import org.apache.axis2.Constants.Configuration;
@@ -37,6 +37,7 @@
 import org.apache.axis2.jaxws.client.async.PollingFuture;
 import org.apache.axis2.jaxws.core.InvocationContext;
 import org.apache.axis2.jaxws.core.MessageContext;
+import org.apache.axis2.jaxws.core.controller.InvocationController;
 import org.apache.axis2.jaxws.description.OperationDescription;
 import org.apache.axis2.jaxws.handler.MEPContext;
 import org.apache.axis2.jaxws.i18n.Messages;
@@ -72,7 +73,7 @@
  * For more information on how to invoke this class, please see the InvocationController interface
  * comments.
  */
-public class AxisInvocationController extends InvocationController {
+public class AxisInvocationController extends InvocationControllerImpl {
 
     private static Log log = LogFactory.getLog(AxisInvocationController.class);
 

Added: webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/core/controller/impl/InvocationControllerFactoryImpl.java
URL: http://svn.apache.org/viewvc/webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/core/controller/impl/InvocationControllerFactoryImpl.java?rev=614697&view=auto
==============================================================================
--- webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/core/controller/impl/InvocationControllerFactoryImpl.java (added)
+++ webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/core/controller/impl/InvocationControllerFactoryImpl.java Wed Jan 23 13:54:02 2008
@@ -0,0 +1,30 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.axis2.jaxws.core.controller.impl;
+
+import org.apache.axis2.jaxws.core.controller.InvocationController;
+import org.apache.axis2.jaxws.core.controller.InvocationControllerFactory;
+
+public class InvocationControllerFactoryImpl implements InvocationControllerFactory {
+    
+    public InvocationController getInvocationController() {
+        return new AxisInvocationController();
+    }
+
+}

Added: webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/core/controller/impl/InvocationControllerImpl.java
URL: http://svn.apache.org/viewvc/webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/core/controller/impl/InvocationControllerImpl.java?rev=614697&view=auto
==============================================================================
--- webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/core/controller/impl/InvocationControllerImpl.java (added)
+++ webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/core/controller/impl/InvocationControllerImpl.java Wed Jan 23 13:54:02 2008
@@ -0,0 +1,300 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.axis2.jaxws.core.controller.impl;
+
+import org.apache.axis2.jaxws.ExceptionFactory;
+import org.apache.axis2.jaxws.core.InvocationContext;
+import org.apache.axis2.jaxws.core.MessageContext;
+import org.apache.axis2.jaxws.core.controller.InvocationController;
+import org.apache.axis2.jaxws.core.controller.InvocationPattern;
+import org.apache.axis2.jaxws.core.util.MessageContextUtils;
+import org.apache.axis2.jaxws.handler.AttachmentsAdapter;
+import org.apache.axis2.jaxws.handler.HandlerChainProcessor;
+import org.apache.axis2.jaxws.handler.HandlerInvokerUtils;
+import org.apache.axis2.jaxws.handler.TransportHeadersAdapter;
+import org.apache.axis2.jaxws.i18n.Messages;
+import org.apache.axis2.jaxws.util.Constants;
+import org.apache.commons.logging.Log;
+import org.apache.commons.logging.LogFactory;
+
+import javax.xml.ws.AsyncHandler;
+import javax.xml.ws.Response;
+
+import java.util.concurrent.ExecutorService;
+import java.util.concurrent.Future;
+
+/**
+ * An abstract implementation of the InvocationController interface. 
+ */
+public abstract class InvocationControllerImpl implements InvocationController {
+
+    private static final Log log = LogFactory.getLog(InvocationControllerImpl.class);
+
+    /*
+     * (non-Javadoc)
+     * @see org.apache.axis2.jaxws.core.controller.InvocationController#invoke(org.apache.axis2.jaxws.core.InvocationContext)
+     */
+    public InvocationContext invoke(InvocationContext ic) {
+        if (log.isDebugEnabled()) {
+            log.debug("Invocation pattern: synchronous");
+        }
+
+        // Check to make sure we at least have a valid InvocationContext
+        // and request MessageContext
+        if (ic == null) {
+            throw ExceptionFactory.makeWebServiceException(Messages.getMessage("ICErr1"));
+        }
+        if (ic.getRequestMessageContext() == null) {
+            throw ExceptionFactory.makeWebServiceException(Messages.getMessage("ICErr2"));
+        }
+
+        MessageContext request = ic.getRequestMessageContext();
+        MessageContext response = null;
+
+        request.setProperty(Constants.INVOCATION_PATTERN, InvocationPattern.SYNC);
+
+        // Invoke outbound handlers.
+        boolean success =
+                HandlerInvokerUtils.invokeOutboundHandlers(request.getMEPContext(),
+                                                           ic.getHandlers(),
+                                                           HandlerChainProcessor.MEP.REQUEST,
+                                                           false);
+
+        if (success) {
+            prepareRequest(request);
+            response = doInvoke(request);
+            prepareResponse(response);
+            
+            // make sure request and response contexts share a single parent
+            response.setMEPContext(request.getMEPContext());
+
+            /*
+             * TODO TODO TODO review
+             * 
+             * In most cases we are adding the endpointDesc to the
+             * MessageContext. Notice here that the "response" object is set by
+             * the call to doInvoke. It's a new context we are now working with.
+             * The invokeInboundHandlers uses that context way down in
+             * createMessageContext --> ContextUtils.addProperties()
+             * 
+             * This may also occur in the AsyncResponse class when calling
+             * invokeInboundHandlers
+             * 
+             * For now, make sure the endpointDesc is set on the response
+             * context.
+             */
+            response.setEndpointDescription(request.getEndpointDescription());
+
+            // Invoke inbound handlers.
+            TransportHeadersAdapter.install(response);
+            AttachmentsAdapter.install(response);
+            HandlerInvokerUtils.invokeInboundHandlers(response.getMEPContext(),
+                                                      ic.getHandlers(),
+                                                      HandlerChainProcessor.MEP.RESPONSE,
+                                                      false);
+        } else { // the outbound handler chain must have had a problem, and
+                    // we've reversed directions
+            response = MessageContextUtils.createMinimalResponseMessageContext(request);
+            // since we've reversed directions, the message has "become a
+            // make sure request and response contexts share a single parent
+            response.setMEPContext(request.getMEPContext());
+            response.setMessage(request.getMessage());
+        }
+        ic.setResponseMessageContext(response);
+        return ic;
+    }
+
+    protected abstract MessageContext doInvoke(MessageContext request);
+
+    /*
+     * (non-Javadoc)
+     * @see org.apache.axis2.jaxws.core.controller.InvocationController#invokeOneWay(org.apache.axis2.jaxws.core.InvocationContext)
+     */
+    public void invokeOneWay(InvocationContext ic) throws Exception {
+        if (log.isDebugEnabled()) {
+            log.debug("Invocation pattern: one-way");
+        }
+
+        // Check to make sure we at least have a valid InvocationContext
+        // and request MessageContext
+        if (ic == null) {
+            throw ExceptionFactory.makeWebServiceException("ICErr1");
+        }
+        if (ic.getRequestMessageContext() == null) {
+            throw ExceptionFactory.makeWebServiceException("ICErr2");
+        }
+
+        MessageContext request = ic.getRequestMessageContext();
+        request.setProperty(Constants.INVOCATION_PATTERN, InvocationPattern.ONEWAY);
+
+        // Invoke outbound handlers.
+        boolean success =
+                HandlerInvokerUtils.invokeOutboundHandlers(request.getMEPContext(),
+                                                           ic.getHandlers(),
+                                                           HandlerChainProcessor.MEP.REQUEST,
+                                                           true);
+
+        if (success) {
+            prepareRequest(request);
+            doInvokeOneWay(request);
+        } else { // the outbound handler chain must have had a problem, and we've reversed directions
+            // check to see if problem is due to a handler throwing an exception.  If so, throw it,
+            // even in this oneWay invoke.
+            Exception e = request.getCausedByException();
+            if (e != null) {
+                throw (Exception)e.getCause();
+            }
+        }
+        return;
+    }
+
+    protected abstract void doInvokeOneWay(MessageContext mc);
+
+    /*
+     * (non-Javadoc)
+     * @see org.apache.axis2.jaxws.core.controller.InvocationController#invokeAsync(org.apache.axis2.jaxws.core.InvocationContext)
+     */
+    public Response invokeAsync(InvocationContext ic) {
+        if (log.isDebugEnabled()) {
+            log.debug("Invocation pattern: asynchronous(polling)");
+        }
+
+        // Check to make sure we at least have a valid InvocationContext
+        // and request MessageContext
+        if (ic == null) {
+            throw ExceptionFactory.makeWebServiceException(Messages.getMessage("ICErr1"));
+        }
+        if (ic.getRequestMessageContext() == null) {
+            throw ExceptionFactory.makeWebServiceException(Messages.getMessage("ICErr2"));
+        }
+
+        MessageContext request = ic.getRequestMessageContext();
+        request.setProperty(Constants.INVOCATION_PATTERN, InvocationPattern.ASYNC_POLLING);
+
+        Response resp = null;
+
+        // Invoke outbound handlers.
+        // TODO uncomment, and get the EndpointDescription from the request context, which should soon be available
+        boolean success =
+                HandlerInvokerUtils.invokeOutboundHandlers(request.getMEPContext(),
+                                                           ic.getHandlers(),
+                                                           HandlerChainProcessor.MEP.REQUEST,
+                                                           false);
+        if (success) {
+            prepareRequest(request);
+            resp = doInvokeAsync(request);
+        } else
+        { // the outbound handler chain must have had a problem, and we've reversed directions
+            // since we've reversed directions, the message has "become a response message" (section 9.3.2.1, footnote superscript 2)
+
+            // TODO we know the message is a fault message, we should
+            // convert it to an exception and throw it.
+            // something like:
+
+            //throw new AxisFault(request.getMessage());
+        }
+
+        return resp;
+    }
+
+    public abstract Response doInvokeAsync(MessageContext mc);
+
+    /*
+     * (non-Javadoc)
+     * @see org.apache.axis2.jaxws.core.controller.InvocationController#invokeAsync(org.apache.axis2.jaxws.core.InvocationContext, javax.xml.ws.AsyncHandler)
+     */
+    public Future<?> invokeAsync(InvocationContext ic, AsyncHandler asyncHandler) {
+        if (log.isDebugEnabled()) {
+            log.debug("Invocation pattern: asynchronous(callback)");
+        }
+
+        // Check to make sure we at least have a valid InvocationContext
+        // and request MessageContext
+        if (ic == null) {
+            throw ExceptionFactory.makeWebServiceException(Messages.getMessage("ICErr1"));
+        }
+        if (ic.getRequestMessageContext() == null) {
+            throw ExceptionFactory.makeWebServiceException(Messages.getMessage("ICErr2"));
+        }
+        if ((ic.getExecutor() != null) && (ic.getExecutor() instanceof ExecutorService)) {
+            ExecutorService es = (ExecutorService) ic.getExecutor();
+            if (es.isShutdown()) {
+                // the executor service is shutdown and won't accept new tasks
+                // so return an error back to the client
+                throw ExceptionFactory.makeWebServiceException(Messages
+                                .getMessage("ExecutorShutdown"));
+            }
+        }
+
+        MessageContext request = ic.getRequestMessageContext();
+        request.setProperty(Constants.INVOCATION_PATTERN, InvocationPattern.ASYNC_CALLBACK);
+
+        Future<?> future = null;
+
+        // Invoke outbound handlers.
+        boolean success =
+                HandlerInvokerUtils.invokeOutboundHandlers(request.getMEPContext(),
+                                                           ic.getHandlers(),
+                                                           HandlerChainProcessor.MEP.REQUEST,
+                                                           false);
+        if (success) {
+            prepareRequest(request);
+            future = doInvokeAsync(request, asyncHandler);
+        } else { // the outbound handler chain must have had a problem, and
+                    // we've reversed directions
+            // since we've reversed directions, the message has "become a
+            // response message" (section 9.3.2.1, footnote superscript 2)
+
+            // TODO: how do we deal with this? The response message may or may
+            // not be a fault
+            // message. We do know that the direction has reversed, so somehow
+            // we need to
+            // flow immediately out of the async and give the exception and/or
+            // response object
+            // back to the client app without calling
+            // AsyncResponse.processResponse or processFault
+                
+            throw ExceptionFactory.makeWebServiceException(Messages.getMessage("invokeAsyncErr"));
+
+            // throw new AxisFault(request.getMessage());
+        }
+        return future;
+    }
+
+    public abstract Future<?> doInvokeAsync(MessageContext mc, AsyncHandler asyncHandler);
+
+    /**
+     * Abstract method that must be implemented by whoever is providing the specific client binding.
+     *  Once this is called, everything that is needed to invoke the operation must be available in
+     * the MessageContext.
+     *
+     * @param mc
+     */
+    protected abstract void prepareRequest(MessageContext mc);
+
+    /**
+     * Abstract method that must be implemented by whoever is providing the specific client binding.
+     *  This is called after the response has come back and allows the client binding to put
+     * whatever info it has in the response MessageContext.
+     *
+     * @param mc
+     */
+    protected abstract void prepareResponse(MessageContext mc);
+
+}

Modified: webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/registry/FactoryRegistry.java
URL: http://svn.apache.org/viewvc/webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/registry/FactoryRegistry.java?rev=614697&r1=614696&r2=614697&view=diff
==============================================================================
--- webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/registry/FactoryRegistry.java (original)
+++ webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/registry/FactoryRegistry.java Wed Jan 23 13:54:02 2008
@@ -19,6 +19,8 @@
 
 package org.apache.axis2.jaxws.registry;
 
+import org.apache.axis2.jaxws.core.controller.InvocationControllerFactory;
+import org.apache.axis2.jaxws.core.controller.impl.InvocationControllerFactoryImpl;
 import org.apache.axis2.jaxws.handler.lifecycle.factory.HandlerLifecycleManagerFactory;
 import org.apache.axis2.jaxws.message.databinding.impl.JAXBBlockFactoryImpl;
 import org.apache.axis2.jaxws.message.databinding.impl.OMBlockFactoryImpl;
@@ -94,6 +96,7 @@
         table.put(ClassFinderFactory.class, new ClassFinderFactory());
         table.put(ExecutorFactory.class, new JAXWSExecutorFactory());
         table.put(ServiceInstanceFactory.class, new ServiceInstanceFactoryImpl());
+        table.put(InvocationControllerFactory.class, new InvocationControllerFactoryImpl());
         
         // register the implementation responsible for both WebServiceContext 
         // injection and the updating of the WebServiceContext instances that

Added: webservices/axis2/trunk/java/modules/jaxws/test/org/apache/axis2/jaxws/client/dispatch/InvocationControllerTest.java
URL: http://svn.apache.org/viewvc/webservices/axis2/trunk/java/modules/jaxws/test/org/apache/axis2/jaxws/client/dispatch/InvocationControllerTest.java?rev=614697&view=auto
==============================================================================
--- webservices/axis2/trunk/java/modules/jaxws/test/org/apache/axis2/jaxws/client/dispatch/InvocationControllerTest.java (added)
+++ webservices/axis2/trunk/java/modules/jaxws/test/org/apache/axis2/jaxws/client/dispatch/InvocationControllerTest.java Wed Jan 23 13:54:02 2008
@@ -0,0 +1,74 @@
+package org.apache.axis2.jaxws.client.dispatch;
+
+import org.apache.axis2.jaxws.core.InvocationContext;
+import org.apache.axis2.jaxws.core.controller.InvocationController;
+import org.apache.axis2.jaxws.core.controller.InvocationControllerFactory;
+import org.apache.axis2.jaxws.core.controller.impl.AxisInvocationController;
+import org.apache.axis2.jaxws.registry.FactoryRegistry;
+
+import javax.xml.namespace.QName;
+import javax.xml.transform.Source;
+import javax.xml.ws.AsyncHandler;
+import javax.xml.ws.Dispatch;
+import javax.xml.ws.Response;
+import javax.xml.ws.Service;
+import javax.xml.ws.soap.SOAPBinding;
+
+import java.util.concurrent.Future;
+
+import junit.framework.TestCase;
+
+public class InvocationControllerTest extends TestCase {
+
+    private QName svcQname = new QName("http://test", "TestService");
+    private QName portQname = new QName("http://test", "TestPort");
+    
+    public void testDefaultInvocationController() {
+        Service svc = Service.create(svcQname);
+        svc.addPort(portQname, SOAPBinding.SOAP11HTTP_BINDING, "http://localhost");
+        Dispatch d = svc.createDispatch(portQname, Source.class, Service.Mode.PAYLOAD);
+        
+        BaseDispatch bd = (BaseDispatch) d;
+        
+        assertTrue("An InvocationController instance was not created", bd.ic != null);
+        assertTrue("The default InvocationController type was incorrect.", 
+            AxisInvocationController.class.isAssignableFrom(bd.ic.getClass()));
+    }
+    
+    public void testPluggableInvocationController() {
+        FactoryRegistry.setFactory(InvocationControllerFactory.class, new TestInvocationControllerFactory());
+        
+        Service svc = Service.create(svcQname);
+        svc.addPort(portQname, SOAPBinding.SOAP11HTTP_BINDING, "http://localhost");
+        Dispatch d = svc.createDispatch(portQname, Source.class, Service.Mode.PAYLOAD);
+        
+        BaseDispatch bd = (BaseDispatch) d;
+        
+        assertTrue("An InvocationController instance was not created", bd.ic != null);
+        assertTrue("The default InvocationController type was incorrect.", 
+            TestInvocationController.class.isAssignableFrom(bd.ic.getClass()));
+    }
+}
+
+class TestInvocationControllerFactory implements InvocationControllerFactory {
+    public InvocationController getInvocationController() {
+        return new TestInvocationController(); 
+    }
+}
+
+class TestInvocationController implements InvocationController {
+
+    public InvocationContext invoke(InvocationContext ic) {
+        return null;
+    }
+
+    public Future<?> invokeAsync(InvocationContext ic, AsyncHandler asyncHandler) {
+        return null;
+    }
+
+    public Response invokeAsync(InvocationContext ic) {
+        return null;
+    }
+
+    public void invokeOneWay(InvocationContext ic) throws Exception {}    
+}



---------------------------------------------------------------------
To unsubscribe, e-mail: axis-cvs-unsubscribe@ws.apache.org
For additional commands, e-mail: axis-cvs-help@ws.apache.org