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 sa...@apache.org on 2006/05/05 11:23:03 UTC

svn commit: r400026 - in /webservices/axis2/trunk/c: modules/core/clientapi/op_client.c modules/core/clientapi/svc_client.c samples/user_guide/clients/Makefile.am samples/user_guide/clients/echo_non_blocking.c

Author: samisa
Date: Fri May  5 02:22:59 2006
New Revision: 400026

URL: http://svn.apache.org/viewcvs?rev=400026&view=rev
Log:
Fixes to get non blocking working with service client

Added:
    webservices/axis2/trunk/c/samples/user_guide/clients/echo_non_blocking.c
Modified:
    webservices/axis2/trunk/c/modules/core/clientapi/op_client.c
    webservices/axis2/trunk/c/modules/core/clientapi/svc_client.c
    webservices/axis2/trunk/c/samples/user_guide/clients/Makefile.am

Modified: webservices/axis2/trunk/c/modules/core/clientapi/op_client.c
URL: http://svn.apache.org/viewcvs/webservices/axis2/trunk/c/modules/core/clientapi/op_client.c?rev=400026&r1=400025&r2=400026&view=diff
==============================================================================
--- webservices/axis2/trunk/c/modules/core/clientapi/op_client.c (original)
+++ webservices/axis2/trunk/c/modules/core/clientapi/op_client.c Fri May  5 02:22:59 2006
@@ -37,12 +37,26 @@
 	axis2_callback_t *callback;
 
 	axis2_bool_t completed;
-
+    /* to hold the locally created async result */
+    axis2_async_result_t *async_result;
 } axis2_op_client_impl_t;
 
 /** Interface to implementation conversion macro */
 #define AXIS2_INTF_TO_IMPL(op_client) ((axis2_op_client_impl_t *)op_client)
 
+typedef struct axis2_op_client_worker_func_args
+{
+    axis2_env_t **env;
+    axis2_op_client_impl_t *op_client_impl;
+    axis2_callback_t *callback;
+    axis2_op_t *op;
+    axis2_msg_ctx_t *msg_ctx;
+} axis2_op_client_worker_func_args_t;
+
+void * AXIS2_THREAD_FUNC
+axis2_op_client_worker_func(axis2_thread_t *thd, void *data);
+
+
 /** private function prototypes */
 static void axis2_op_client_init_ops(axis2_op_client_t *op_client);
 static axis2_msg_ctx_t* axis2_op_client_invoke_blocking(axis2_op_client_impl_t *op_client_impl,
@@ -122,6 +136,7 @@
 	op_client_impl->op_ctx = NULL;
     op_client_impl->callback = NULL;
     op_client_impl->completed = AXIS2_FALSE;
+    op_client_impl->async_result = NULL;
     
 	op_client_impl->options = options;
 	op_client_impl->svc_ctx = svc_ctx;
@@ -286,8 +301,7 @@
     axis2_op_client_impl_t *op_client_impl = NULL;
    	axis2_conf_ctx_t *conf_ctx = NULL;
    	axis2_msg_ctx_t *msg_ctx = NULL;
-	axis2_msg_info_headers_t *msg_info_headers = NULL;
-	
+
 	axis2_transport_out_desc_t *transport_out = NULL;
 	axis2_transport_in_desc_t *transport_in = NULL;
 
@@ -388,7 +402,6 @@
 	{
 		if (block)
 		{
-			axis2_op_ctx_t *op_ctx = NULL;
         	axis2_msg_ctx_t *response_mc = NULL;
         	axis2_char_t *address = NULL;
         	axis2_char_t *epr_address = NULL;
@@ -403,24 +416,54 @@
         	AXIS2_PROPERTY_SET_VALUE(property, env, address);
         	AXIS2_MSG_CTX_SET_PROPERTY(msg_ctx, env,
                 AXIS2_TRANSPORT_URL, property, AXIS2_FALSE);
-        	/*AXIS2_MSG_CTX_SET_TO(msg_ctx, env, call_impl->to);*/
         	AXIS2_MSG_CTX_SET_SVC_CTX(msg_ctx, env, op_client_impl->svc_ctx);
         	AXIS2_MSG_CTX_SET_CONF_CTX(msg_ctx, env, 
                 AXIS2_SVC_CTX_GET_CONF_CTX(op_client_impl->svc_ctx, env));
             AXIS2_MSG_CTX_SET_OP_CTX(msg_ctx, env, op_client_impl->op_ctx);
 
-			/*TODO: check this if it is necessary*/
-        	/*op_ctx = axis2_op_ctx_create(env, op, op_client_impl->svc_ctx);
-        	AXIS2_OP_REGISTER_OP_CTX(op, env, msg_ctx, op_ctx);*/
-
-        	/*Send the SOAP Message and receive a response */
+            /*Send the SOAP Message and receive a response */
         	response_mc = axis2_mep_client_two_way_send(env, msg_ctx);
         	if (!response_mc)
             	return AXIS2_FAILURE;
-			axis2_op_client_add_msg_ctx(&(op_client_impl->op_client), env, response_mc);	
+			axis2_op_client_add_msg_ctx(&(op_client_impl->op_client), env, 
+                response_mc);	
 		}
 		else
 		{
+            axis2_thread_t *worker_thread = NULL;
+            axis2_op_client_worker_func_args_t *arg_list = NULL;
+            arg_list = AXIS2_MALLOC((*env)->allocator, 
+                            sizeof(axis2_op_client_worker_func_args_t));
+            if(NULL == arg_list)
+            {
+                return AXIS2_FAILURE;			
+            }
+            arg_list->env = env;
+            arg_list->op_client_impl = op_client_impl;
+            arg_list->callback = op_client_impl->callback;
+            arg_list->op = op;
+            arg_list->msg_ctx = msg_ctx;
+#ifdef AXIS2_SVR_MULTI_THREADED
+            if ((*env)->thread_pool)
+            {
+                worker_thread = AXIS2_THREAD_POOL_GET_THREAD((*env)->thread_pool,
+                                                 axis2_op_client_worker_func, (void*)arg_list);
+                if(NULL == worker_thread)
+                {
+                    AXIS2_LOG_ERROR((*env)->log, AXIS2_LOG_SI, "Thread creation failed"
+                                     "call invoke non blocking");
+                }
+                AXIS2_THREAD_POOL_THREAD_DETACH((*env)->thread_pool, worker_thread);
+            }
+            else
+            {
+                AXIS2_LOG_ERROR((*env)->log, AXIS2_LOG_SI, "Thread pool not set in envioronment."
+                                             " Cannot invoke call non blocking");
+            }
+#else
+            axis2_op_client_worker_func(NULL, (void*)arg_list);
+#endif
+            
 		}
 	}
 	return AXIS2_SUCCESS;
@@ -523,4 +566,36 @@
 										axis2_msg_ctx_t *mc)
 {
 	return NULL;
+}
+
+void * AXIS2_THREAD_FUNC
+axis2_op_client_worker_func(axis2_thread_t *thd, void *data)
+{
+    axis2_op_client_worker_func_args_t *args_list = NULL;
+    axis2_op_ctx_t *op_ctx = NULL;
+    axis2_msg_ctx_t *response = NULL;
+	axis2_env_t **thread_env = NULL;
+	axis2_env_t *th_env = NULL;
+    
+    args_list = (axis2_op_client_worker_func_args_t *) data;
+    if (!args_list)
+        return NULL;
+        
+    AXIS2_ENV_CHECK(args_list->env, AXIS2_FAILURE);
+	th_env = axis2_init_thread_env(args_list->env);
+    thread_env = &th_env;
+
+    op_ctx = axis2_op_ctx_create(thread_env, args_list->op, args_list->op_client_impl->svc_ctx);
+    if (!op_ctx)
+        return NULL;
+    AXIS2_MSG_CTX_SET_OP_CTX(args_list->msg_ctx, thread_env, op_ctx);
+    AXIS2_MSG_CTX_SET_SVC_CTX(args_list->msg_ctx, thread_env, args_list->op_client_impl->svc_ctx);
+
+    /* send the request and wait for reponse */
+    response = axis2_mep_client_two_way_send(thread_env, args_list->msg_ctx);
+    args_list->op_client_impl->async_result = axis2_async_result_create(thread_env, response);
+    AXIS2_CALLBACK_INVOKE_ON_COMPLETE(args_list->callback, thread_env, args_list->op_client_impl->async_result);
+    AXIS2_CALLBACK_SET_COMPLETE(args_list->callback, thread_env, AXIS2_TRUE);
+    
+    return NULL; 
 }

Modified: webservices/axis2/trunk/c/modules/core/clientapi/svc_client.c
URL: http://svn.apache.org/viewcvs/webservices/axis2/trunk/c/modules/core/clientapi/svc_client.c?rev=400026&r1=400025&r2=400026&view=diff
==============================================================================
--- webservices/axis2/trunk/c/modules/core/clientapi/svc_client.c (original)
+++ webservices/axis2/trunk/c/modules/core/clientapi/svc_client.c Fri May  5 02:22:59 2006
@@ -558,14 +558,14 @@
                     axis2_om_node_t *payload)
 {
 	axis2_svc_client_impl_t *svc_client_impl = NULL;
-	axis2_qname_t *op = NULL;
+	axis2_qname_t *op_qname = NULL;
 	AXIS2_ENV_CHECK(env, NULL);
 
 	svc_client_impl = AXIS2_INTF_TO_IMPL(svc_client);
-	op = axis2_qname_create(env, AXIS2_ANON_OUT_IN_OP, NULL, NULL);
+	op_qname = axis2_qname_create(env, AXIS2_ANON_OUT_IN_OP, NULL, NULL);
 	
 	return axis2_svc_client_send_receive_with_op_qname(
-			&(svc_client_impl->svc_client), env, op, payload);
+			&(svc_client_impl->svc_client), env, op_qname, payload);
 }
 
 
@@ -589,19 +589,26 @@
 	{
 		axis2_op_client_t *op_client = NULL;
 		axis2_msg_ctx_t *res_msg_ctx = NULL;
-		axis2_msg_ctx_t *mc = NULL;
+		axis2_msg_ctx_t *msg_ctx = NULL;
 		axis2_soap_envelope_t *soap_envelope = NULL;
 		axis2_soap_body_t *soap_body = NULL;
 		axis2_om_node_t *soap_node = NULL;
 
-		mc = axis2_msg_ctx_create(env, 
-				AXIS2_SVC_CTX_GET_CONF_CTX(svc_client_impl->svc_ctx, env), NULL, NULL);
-		if (!axis2_svc_client_fill_soap_envelope(env, svc_client_impl, mc, payload))
+        msg_ctx = axis2_msg_ctx_create(env, 
+            AXIS2_SVC_CTX_GET_CONF_CTX(svc_client_impl->svc_ctx, env), NULL, NULL);
+		if (!axis2_svc_client_fill_soap_envelope(env, svc_client_impl, msg_ctx, 
+            payload))
+        {
 			return NULL;
+        }
 		
 		op_client = axis2_svc_client_create_op_client(&(svc_client_impl->svc_client), env, op_qname);
-		
-		AXIS2_OP_CLIENT_ADD_MSG_CTX(op_client, env, mc);
+		if (!op_client)
+        {
+            return NULL;
+        }
+        
+		AXIS2_OP_CLIENT_ADD_MSG_CTX(op_client, env, msg_ctx);
 		AXIS2_OP_CLIENT_EXECUTE(op_client, env, AXIS2_TRUE);
 		res_msg_ctx = AXIS2_OP_CTX_GET_MSG_CTX(op_client, env, AXIS2_WSDL_MESSAGE_LABEL_IN_VALUE);
 		
@@ -638,7 +645,16 @@
                     axis2_om_node_t *payload,
                     axis2_callback_t *callback)
 {
+    axis2_svc_client_impl_t *svc_client_impl = NULL;
+	axis2_qname_t *op_qname = NULL;
+	AXIS2_ENV_CHECK(env, NULL);
 
+	svc_client_impl = AXIS2_INTF_TO_IMPL(svc_client);
+	op_qname = axis2_qname_create(env, AXIS2_ANON_OUT_IN_OP, NULL, NULL);
+	
+	axis2_svc_client_send_receive_non_blocking_with_operation(
+			&(svc_client_impl->svc_client), env, op_qname, payload, callback);
+    return;
 }
 
 void AXIS2_CALL 
@@ -648,7 +664,41 @@
                     axis2_om_node_t *payload,
                     axis2_callback_t *callback)
 {
+    axis2_svc_client_impl_t *svc_client_impl = NULL;
+    axis2_op_client_t *op_client = NULL;
+	axis2_msg_ctx_t *res_msg_ctx = NULL;
+    axis2_msg_ctx_t *msg_ctx = NULL;
+    axis2_soap_envelope_t *soap_envelope = NULL;
+    axis2_soap_body_t *soap_body = NULL;
+    axis2_om_node_t *soap_node = NULL;
+
+	AXIS2_ENV_CHECK(env, NULL);
 
+	svc_client_impl = AXIS2_INTF_TO_IMPL(svc_client);
+
+    msg_ctx = axis2_msg_ctx_create(env, 
+    AXIS2_SVC_CTX_GET_CONF_CTX(svc_client_impl->svc_ctx, env), NULL, NULL);
+    if (!axis2_svc_client_fill_soap_envelope(env, svc_client_impl, msg_ctx, payload))
+        return;
+    
+    op_client = axis2_svc_client_create_op_client(&(svc_client_impl->svc_client), 
+        env, op_qname);
+    if (!op_client)
+    {
+        return;
+    }
+
+    AXIS2_OP_CLIENT_SET_CALLBACK(op_client, env, callback);
+    AXIS2_OP_CLIENT_ADD_MSG_CTX(op_client, env, msg_ctx);
+    
+    if (AXIS2_OPTIONS_IS_USE_SEPERATE_LISTENER(svc_client_impl->options, env))
+    {
+		return;
+	}
+    
+    AXIS2_OP_CLIENT_EXECUTE(op_client, env, AXIS2_FALSE);
+    
+    return;
 }
 
 axis2_op_client_t* AXIS2_CALL 

Modified: webservices/axis2/trunk/c/samples/user_guide/clients/Makefile.am
URL: http://svn.apache.org/viewcvs/webservices/axis2/trunk/c/samples/user_guide/clients/Makefile.am?rev=400026&r1=400025&r2=400026&view=diff
==============================================================================
--- webservices/axis2/trunk/c/samples/user_guide/clients/Makefile.am (original)
+++ webservices/axis2/trunk/c/samples/user_guide/clients/Makefile.am Fri May  5 02:22:59 2006
@@ -1,9 +1,10 @@
 prgbindir=$(prefix)/bin/samples
-prgbin_PROGRAMS = echo_blocking echo_blocking_addr echo_rest
+prgbin_PROGRAMS = echo_blocking echo_non_blocking echo_blocking_addr echo_rest
 samplesdir=$(prefix)/samples/user_guide/clients
-samples_DATA=echo_util.h echo_util.c echo_blocking.c echo_blocking_addr.c echo_rest.c Makefile.am Makefile.in
+samples_DATA=echo_util.h echo_util.c echo_blocking.c echo_non_blocking.c echo_blocking_addr.c echo_rest.c Makefile.am Makefile.in
 
 echo_blocking_SOURCES = echo_blocking.c echo_util.c
+echo_non_blocking_SOURCES = echo_non_blocking.c echo_util.c
 echo_blocking_addr_SOURCES = echo_blocking_addr.c echo_util.c
 echo_rest_SOURCES = echo_util.c echo_rest.c
 
@@ -23,6 +24,7 @@
              $(LIBXML2_LIBS)
 
 echo_blocking_LDADD = $(LINK_FLAGS)
+echo_non_blocking_LDADD = $(LINK_FLAGS)
 echo_blocking_addr_LDADD = $(LINK_FLAGS)
 echo_rest_LDADD = $(LINK_FLAGS)
 

Added: webservices/axis2/trunk/c/samples/user_guide/clients/echo_non_blocking.c
URL: http://svn.apache.org/viewcvs/webservices/axis2/trunk/c/samples/user_guide/clients/echo_non_blocking.c?rev=400026&view=auto
==============================================================================
--- webservices/axis2/trunk/c/samples/user_guide/clients/echo_non_blocking.c (added)
+++ webservices/axis2/trunk/c/samples/user_guide/clients/echo_non_blocking.c Fri May  5 02:22:59 2006
@@ -0,0 +1,209 @@
+/*
+ * Copyright 2004,2005 The Apache Software Foundation.
+ *
+ * Licensed 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.
+ */
+
+#include "echo_util.h"
+#include <axis2_util.h>
+#include <axis2_soap.h>
+#include <axis2_client.h>
+
+/* my on_complete callback function */
+axis2_status_t AXIS2_CALL
+echo_callback_on_complete(struct axis2_callback *callback,
+    axis2_env_t **env);
+
+/* my on_error callback function */
+axis2_status_t AXIS2_CALL
+echo_callback_on_error(struct axis2_callback *callback,
+    axis2_env_t **env,
+    int exception);
+
+/* to check whether the callback is completed */
+int isComplete = 0;
+
+int main(int argc, char** argv)
+{
+    axis2_env_t *env = NULL;
+    axis2_char_t *address = NULL;
+    axis2_endpoint_ref_t* endpoint_ref = NULL;
+    axis2_options_t *options = NULL;
+    axis2_char_t *client_home = NULL;
+    axis2_svc_client_t* svc_client = NULL;
+    axis2_om_node_t *payload = NULL;
+    axis2_callback_t *callback = NULL;
+    int count = 0;
+   
+    /* Set up the envioronment */
+    env = axis2_env_create_all("echo_blocking.log", AXIS2_LOG_LEVEL_TRACE);
+
+    /* Set end point reference of echo service */
+    address = "http://localhost:9090/axis2/services/echo";
+    if (argc > 1 )
+        address = argv[1];
+    if (AXIS2_STRCMP(address, "-h") == 0)
+    {
+        printf("Usage : %s [endpoint_url]\n", argv[0]);
+        printf("use -h for help\n");
+        return 0;
+    }
+    printf ("Using endpoint : %s\n", address);
+    
+    /* Create EPR with given address */
+    endpoint_ref = axis2_endpoint_ref_create(&env, address);
+
+    /* Setup options */
+    options = axis2_options_create(&env);
+    AXIS2_OPTIONS_SET_TO(options, &env, endpoint_ref);
+
+    /* Set up deploy folder. It is from the deploy folder, the configuration is picked up 
+     * using the axis2.xml file.
+     * In this sample client_home points to the Axis2/C default deploy folder. The client_home can 
+     * be different from this folder on your system. For example, you may have a different folder 
+     * (say, my_client_folder) with its own axis2.xml file. my_client_folder/modules will have the 
+     * modules that the client uses
+     */
+    client_home = AXIS2_GETENV("AXIS2C_HOME");
+    if (!client_home)
+        client_home = "../../deploy";
+
+    /* Create service client */
+    svc_client = axis2_svc_client_create(&env, client_home);
+    if (!svc_client)
+    {
+        printf("Error creating service client\n");
+        AXIS2_LOG_ERROR(env->log, AXIS2_LOG_SI, "Stub invoke FAILED: Error code:"
+						" %d :: %s", env->error->error_number,
+                        AXIS2_ERROR_GET_MESSAGE(env->error));
+    }
+
+    /* Set service client options */
+    AXIS2_SVC_CLIENT_SET_OPTIONS(svc_client, &env, options);    
+
+    /* Build the SOAP request message payload using OM API.*/
+    payload = build_om_payload_for_echo_svc(&env);
+    
+    /* Create the callback object with default on_complete and on_error 
+       callback functions */
+    callback = axis2_callback_create(&env);
+	
+	/* Set our on_complete fucntion pointer to the callback object */
+	AXIS2_CALLBACK_SET_ON_COMPLETE(callback, echo_callback_on_complete);
+
+	/* Set our on_error function pointer to the callback object */
+	AXIS2_CALLBACK_SET_ON_ERROR(callback, echo_callback_on_error);
+
+    
+    /* Send request */
+    AXIS2_SVC_CLIENT_SEND_RECEIVE_NON_BLOCKING(svc_client, &env, 
+        payload, callback);
+        
+    /** Wait till callback is complete. Simply keep the parent thread running
+	    until our on_complete or on_error is invoked */
+	while(count < 30 )
+	{
+		if (isComplete)
+		{
+			/* We are done with the callback */
+			break;
+		}
+        AXIS2_SLEEP(1);
+        count++;
+	}
+    
+    if (!(count < 30))
+    {
+        printf("\necho client invike FAILED. Counter timed out.\n");
+    }
+    
+    if (svc_client)
+    {
+        AXIS2_SVC_CLIENT_FREE(svc_client, &env);
+        svc_client = NULL;
+    }
+    
+    if (endpoint_ref)
+    {
+        AXIS2_ENDPOINT_REF_FREE(endpoint_ref, &env);
+        endpoint_ref = NULL;
+    }
+    
+    if (callback)
+    {
+        AXIS2_CALLBACK_FREE(callback, &env);
+        callback = NULL;
+    }
+    
+    return 0;
+}
+
+axis2_status_t AXIS2_CALL
+echo_callback_on_complete(struct axis2_callback *callback,
+                                  axis2_env_t **env)
+{
+	/** SOAP response has arrived here; get the soap envelope 
+	  from the callback object and do whatever you want to do with it */
+	
+	axis2_soap_envelope_t *soap_envelope = NULL;
+	axis2_om_node_t *ret_node = NULL;
+    axis2_status_t status = AXIS2_SUCCESS;
+	
+	printf("inside on_complete_callback function\n");
+	
+	soap_envelope = AXIS2_CALLBACK_GET_ENVELOPE(callback, env);
+	
+	if (!soap_envelope)
+	{
+		 AXIS2_LOG_ERROR((*env)->log, AXIS2_LOG_SI, "Stub invoke FAILED: Error code:"
+                     " %d :: %s", (*env)->error->error_number,
+                     AXIS2_ERROR_GET_MESSAGE((*env)->error));
+		printf("echo stub invoke FAILED!\n");
+		status = AXIS2_FAILURE;
+	}
+    else
+    {
+        ret_node = AXIS2_SOAP_ENVELOPE_GET_BASE_NODE(soap_envelope, env);
+    
+        if(!ret_node)
+        {
+            AXIS2_LOG_ERROR((*env)->log, AXIS2_LOG_SI, "Stub invoke FAILED: Error code:"
+                          " %d :: %s", (*env)->error->error_number,
+                          AXIS2_ERROR_GET_MESSAGE((*env)->error));
+            printf("echo stub invoke FAILED!\n");
+            status = AXIS2_FAILURE;
+        }
+        else
+        {
+            axis2_char_t *om_str = NULL;
+            om_str = AXIS2_OM_NODE_TO_STRING(ret_node, env);
+            if (om_str)
+                printf("\nReceived OM : %s\n", om_str);
+            printf("\necho client invoke SUCCESSFUL!\n");
+        }
+    }    
+    isComplete = 1;
+	return status;
+}
+
+axis2_status_t AXIS2_CALL
+echo_callback_on_error(struct axis2_callback *callback,
+                            axis2_env_t **env,
+                            int exception)
+{
+	/** take necessary action on error */
+	printf("\necho client invike FAILED. Error code:%d ::%s", exception, 
+			AXIS2_ERROR_GET_MESSAGE((*env)->error));
+	isComplete = 1;
+	return AXIS2_SUCCESS;
+}