/* * 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. */ #include #include #include #include #include "../deployment/axis2_desc_builder.h" #include #include #include struct axis2_svc { axis2_svc_grp_t *parent; axis2_char_t *axis_svc_name; /** To keep last update time of the service */ long last_update; axis2_char_t *filename; /** To store module descriptions at deploy time parsing */ axutil_array_list_t *module_list; /** Service description */ axis2_char_t *svc_desc; /** wsdl file path */ axis2_char_t *wsdl_path; /** service folder path */ axis2_char_t *folder_path; /** * WSDL related stuff */ axutil_hash_t *ns_map; /* Count of the entries in the namespace map */ int ns_count; /* To keep the XML scheama either from WSDL or * C2WSDL(in the future) */ axutil_array_list_t *schema_list; /** * A table that keeps a mapping of unique XSD names (Strings) * against the schema objects. This is populated in the first * instance the schemas are asked for and then used to serve * the subsequent requests */ axutil_hash_t *schema_mapping_table; /** * This is where operations are kept */ axutil_hash_t *op_alias_map; /** * This is where action mappings are kept */ axutil_hash_t *op_action_map; /** * This is where REST mappings are kept */ axutil_hash_t *op_rest_map; /** * Keeps track whether the schema locations are adjusted */ axis2_bool_t schema_loc_adjusted; /** * A custom schema name prefix. if set this will be used to * modify the schema names */ axis2_char_t *custom_schema_name_prefix; /** * A custom schema name suffix. will be attached to the * schema file name when the files are uniquely named. * A good place to add a file extension if needed */ axis2_char_t *custom_schema_name_suffix; /* To store the target namespace for the schema */ axis2_char_t *schema_target_ns; axis2_char_t *schema_target_ns_prefix; /* To keep the service target name space */ axis2_char_t *target_ns; axis2_char_t *target_ns_prefix; /* Used for schema name calculations */ int sc_calc_count; void *impl_class; axutil_qname_t *qname; axis2_char_t *style; axutil_array_list_t *engaged_module_list; /** Parameter container to hold service related parameters */ struct axutil_param_container *param_container; /** Flow container that encapsulates the flow related data */ struct axis2_flow_container *flow_container; /** Base description struct */ axis2_desc_t *base; /* Mutex to avoid loading the same service dll twice */ axutil_thread_mutex_t *mutex; }; AXIS2_EXTERN axis2_svc_t *AXIS2_CALL axis2_svc_create( const axutil_env_t * env) { axis2_svc_t *svc = NULL; svc = (axis2_svc_t *)AXIS2_MALLOC(env->allocator, sizeof(axis2_svc_t)); if(!svc) { AXIS2_ERROR_SET(env->error, AXIS2_ERROR_NO_MEMORY, AXIS2_FAILURE); AXIS2_LOG_ERROR(env->log, AXIS2_LOG_SI, "No memory"); return NULL; } svc->parent = NULL; svc->axis_svc_name = NULL; svc->filename = NULL; svc->svc_desc = NULL; svc->wsdl_path = NULL; svc->folder_path = NULL; svc->last_update = 0; svc->param_container = NULL; svc->flow_container = NULL; svc->op_alias_map = NULL; svc->op_action_map = NULL; svc->op_rest_map = NULL; svc->module_list = NULL; svc->ns_map = NULL; svc->ns_count = 0; svc->schema_list = NULL; svc->schema_mapping_table = NULL; svc->schema_loc_adjusted = AXIS2_FALSE; svc->custom_schema_name_prefix = NULL; svc->custom_schema_name_suffix = NULL; svc->schema_target_ns = NULL; svc->schema_target_ns_prefix = NULL; svc->target_ns = NULL; svc->target_ns_prefix = NULL; svc->sc_calc_count = 0; svc->impl_class = NULL; svc->qname = NULL; svc->style = NULL; svc->base = NULL; svc->param_container = axutil_param_container_create(env); if(!svc->param_container) { axis2_svc_free(svc, env); AXIS2_ERROR_SET(env->error, AXIS2_ERROR_NO_MEMORY, AXIS2_FAILURE); AXIS2_LOG_ERROR(env->log, AXIS2_LOG_SI, "Service param container creation failed"); return NULL; } svc->flow_container = axis2_flow_container_create(env); if(!svc->flow_container) { axis2_svc_free(svc, env); AXIS2_ERROR_SET(env->error, AXIS2_ERROR_NO_MEMORY, AXIS2_FAILURE); AXIS2_LOG_ERROR(env->log, AXIS2_LOG_SI, "Service flow container creation failed"); return NULL; } svc->op_alias_map = axutil_hash_make(env); if(!svc->op_alias_map) { axis2_svc_free(svc, env); AXIS2_ERROR_SET(env->error, AXIS2_ERROR_NO_MEMORY, AXIS2_FAILURE); AXIS2_LOG_ERROR(env->log, AXIS2_LOG_SI, "Service operation alias map creation failed"); return NULL; } svc->op_action_map = axutil_hash_make(env); if(!svc->op_action_map) { axis2_svc_free(svc, env); AXIS2_ERROR_SET(env->error, AXIS2_ERROR_NO_MEMORY, AXIS2_FAILURE); AXIS2_LOG_ERROR(env->log, AXIS2_LOG_SI, "Service operation action map creation failed"); return NULL; } svc->op_rest_map = axutil_hash_make(env); if(!svc->op_rest_map) { axis2_svc_free(svc, env); AXIS2_ERROR_SET(env->error, AXIS2_ERROR_NO_MEMORY, AXIS2_FAILURE); AXIS2_LOG_ERROR(env->log, AXIS2_LOG_SI, "Service operation rest map creation failed"); return NULL; } /** Create module list of default size */ svc->module_list = axutil_array_list_create(env, 0); if(!svc->module_list) { axis2_svc_free(svc, env); AXIS2_ERROR_SET(env->error, AXIS2_ERROR_NO_MEMORY, AXIS2_FAILURE); AXIS2_LOG_ERROR(env->log, AXIS2_LOG_SI, "Service module list creation failed"); return NULL; } svc->schema_list = axutil_array_list_create(env, AXIS2_ARRAY_LIST_DEFAULT_CAPACITY); if(!svc->schema_list) { axis2_svc_free(svc, env); AXIS2_LOG_ERROR(env->log, AXIS2_LOG_SI, "Service schema list creation failed"); return NULL; } svc->engaged_module_list = axutil_array_list_create(env, AXIS2_ARRAY_LIST_DEFAULT_CAPACITY); if(!svc->engaged_module_list) { axis2_svc_free(svc, env); AXIS2_LOG_ERROR(env->log, AXIS2_LOG_SI, "Service engaged modules list creation failed"); return NULL; } svc->schema_loc_adjusted = AXIS2_FALSE; if(svc->schema_target_ns_prefix) { AXIS2_FREE(env->allocator, svc->schema_target_ns_prefix); svc->schema_target_ns_prefix = NULL; } svc->schema_target_ns_prefix = axutil_strdup(env, "ns"); if(svc->target_ns) { AXIS2_FREE(env->allocator, svc->target_ns); svc->target_ns = NULL; } svc->target_ns = axutil_strdup(env, "http://ws.apache.org/axis2"); if(svc->target_ns_prefix) { AXIS2_FREE(env->allocator, svc->target_ns_prefix); svc->target_ns_prefix = NULL; } svc->target_ns_prefix = axutil_strdup(env, "tns"); svc->sc_calc_count = 0; svc->base = axis2_desc_create(env); if(!svc->base) { axis2_svc_free(svc, env); AXIS2_LOG_ERROR(env->log, AXIS2_LOG_SI, "Service base creation failed"); return NULL; } svc->mutex = axutil_thread_mutex_create(env->allocator, AXIS2_THREAD_MUTEX_DEFAULT); if(!svc->mutex) { axis2_svc_free(svc, env); AXIS2_LOG_ERROR(env->log, AXIS2_LOG_SI, "Service mutex creation failed"); return NULL; } return svc; } AXIS2_EXTERN axis2_svc_t *AXIS2_CALL axis2_svc_create_with_qname( const axutil_env_t * env, const axutil_qname_t * qname) { axis2_svc_t *svc = NULL; axis2_status_t status = AXIS2_FAILURE; AXIS2_PARAM_CHECK(env->error, qname, NULL); svc = axis2_svc_create(env); if(!svc) { AXIS2_ERROR_SET(env->error, AXIS2_ERROR_NO_MEMORY, AXIS2_FAILURE); AXIS2_LOG_ERROR(env->log, AXIS2_LOG_SI, "Service creation failed for name %s", axutil_qname_get_localpart(qname, env)); return NULL; } status = axis2_svc_set_qname(svc, env, qname); if(AXIS2_FAILURE == status) { axis2_svc_free(svc, env); AXIS2_LOG_ERROR(env->log, AXIS2_LOG_SI, "Setting name %s to service failed", axutil_qname_get_localpart(qname, env)); return NULL; } return svc; } AXIS2_EXTERN void AXIS2_CALL axis2_svc_free( axis2_svc_t * svc, const axutil_env_t * env) { if(svc->impl_class) { AXIS2_SVC_SKELETON_FREE((axis2_svc_skeleton_t *)svc->impl_class, env); } if(svc->param_container) { axutil_param_container_free(svc->param_container, env); } if(svc->flow_container) { axis2_flow_container_free(svc->flow_container, env); } if(svc->filename) { AXIS2_FREE(env->allocator, svc->filename); svc->filename = NULL; } if(svc->svc_desc) { AXIS2_FREE(env->allocator, svc->svc_desc); svc->svc_desc = NULL; } svc->parent = NULL; if(svc->module_list) { int i = 0; int size = 0; size = axutil_array_list_size(svc->module_list, env); for(i = 0; i < size; i++) { axutil_qname_t *qname = NULL; qname = axutil_array_list_get(svc->module_list, env, i); if(qname) { axutil_qname_free(qname, env); } } axutil_array_list_free(svc->module_list, env); } if(svc->schema_list) { axutil_array_list_free(svc->schema_list, env); } if(svc->engaged_module_list) { axutil_array_list_free(svc->engaged_module_list, env); } if(svc->axis_svc_name) { AXIS2_FREE(env->allocator, svc->axis_svc_name); svc->axis_svc_name = NULL; } if(svc->op_alias_map) { axutil_hash_index_t *hi = NULL; void *val = NULL; for(hi = axutil_hash_first(svc->op_alias_map, env); hi; hi = axutil_hash_next(env, hi)) { axutil_hash_this(hi, NULL, NULL, &val); if(val) { if(axis2_op_is_from_module((axis2_op_t *)val, env) == AXIS2_FALSE) { axis2_op_free((axis2_op_t *)val, env); } val = NULL; } } axutil_hash_free(svc->op_alias_map, env); } if(svc->op_action_map) { axutil_hash_index_t *hi = NULL; const void *key = NULL; for(hi = axutil_hash_first(svc->op_action_map, env); hi; hi = axutil_hash_next(env, hi)) { axutil_hash_this(hi, &key, NULL, NULL); if(key) { AXIS2_FREE(env->allocator, (axis2_char_t *)key); key = NULL; } } axutil_hash_free(svc->op_action_map, env); } if(svc->op_rest_map) { axis2_core_utils_free_rest_map(env, svc->op_rest_map); } if(svc->schema_target_ns_prefix) { AXIS2_FREE(env->allocator, svc->schema_target_ns_prefix); svc->schema_target_ns_prefix = NULL; } if(svc->target_ns) { AXIS2_FREE(env->allocator, svc->target_ns); svc->target_ns = NULL; } if(svc->wsdl_path) { AXIS2_FREE(env->allocator, svc->wsdl_path); svc->wsdl_path = NULL; } if(svc->folder_path) { AXIS2_FREE(env->allocator, svc->folder_path); svc->folder_path = NULL; } if(svc->target_ns_prefix) { AXIS2_FREE(env->allocator, svc->target_ns_prefix); svc->target_ns_prefix = NULL; } if(svc->qname) { axutil_qname_free(svc->qname, env); } if(svc->style) { AXIS2_FREE(env->allocator, svc->style); } if(svc->base) { axis2_desc_free(svc->base, env); } if(svc->mutex) { axutil_thread_mutex_destroy(svc->mutex); } if(svc) { AXIS2_FREE(env->allocator, svc); svc = NULL; } return; } AXIS2_EXTERN axis2_status_t AXIS2_CALL axis2_svc_add_op( axis2_svc_t * svc, const axutil_env_t * env, axis2_op_t * op) { axis2_status_t status = AXIS2_FAILURE; axis2_msg_recv_t *msg_recv = NULL; const axutil_qname_t *qname = NULL; axis2_char_t *key = NULL; const axis2_char_t *svcname = NULL; axutil_array_list_t *mappings_list = NULL; int size = 0; int j = 0; AXIS2_PARAM_CHECK(env->error, op, AXIS2_FAILURE); svcname = axis2_svc_get_name(svc, env); qname = axis2_op_get_qname(op, env); if(qname) key = axutil_qname_get_localpart(qname, env); mappings_list = axis2_op_get_wsamapping_list(op, env); /* Adding action mappings into service */ if(mappings_list) size = axutil_array_list_size(mappings_list, env); for(j = 0; j < size; j++) { axis2_char_t *mapping = NULL; mapping = (axis2_char_t *)axutil_array_list_get(mappings_list, env, j); status = axis2_svc_add_mapping(svc, env, mapping, op); if(AXIS2_SUCCESS != status) { AXIS2_LOG_ERROR(env->log, AXIS2_LOG_SI, "Adding operation %s to service %s mapping list failed", svcname, key); return status; } } status = axis2_op_set_parent(op, env, svc); if(AXIS2_SUCCESS != status) { AXIS2_LOG_ERROR(env->log, AXIS2_LOG_SI, "Setting service %s as operation %s parent failed", svcname, key); return status; } msg_recv = axis2_op_get_msg_recv(op, env); if(msg_recv == NULL) { msg_recv = axis2_desc_builder_load_default_msg_recv(env); axis2_op_set_msg_recv(op, env, msg_recv); } if(key) { /* If service defines the operation, then we should not override with module level * operation. Module operations are global. If any setting to be modified, those operations * can be defined in service */ if(!axutil_hash_get(svc->op_alias_map, key, AXIS2_HASH_KEY_STRING)) { axutil_hash_set(svc->op_alias_map, key, AXIS2_HASH_KEY_STRING, op); } } return AXIS2_SUCCESS; } AXIS2_EXTERN axis2_op_t *AXIS2_CALL axis2_svc_get_op_with_qname( const axis2_svc_t * svc, const axutil_env_t * env, const axutil_qname_t * op_qname) { axis2_op_t *op = NULL; axis2_char_t *nc_name = NULL; axis2_char_t *nc_tmp = NULL; /* This is just for the sake of comparison, * and must not be used to change the passed value */ axis2_bool_t is_matched = AXIS2_FALSE; AXIS2_PARAM_CHECK(env->error, op_qname, NULL); nc_name = axutil_qname_get_localpart(op_qname, env); nc_tmp = nc_name; op = axutil_hash_get(svc->op_alias_map, nc_tmp, AXIS2_HASH_KEY_STRING); if(op) { return op; } op = axutil_hash_get(svc->op_action_map, nc_tmp, AXIS2_HASH_KEY_STRING); if(op) { return op; } if(*nc_tmp && svc->op_action_map) { axutil_hash_index_t *hi = NULL; const void *key = NULL; for(hi = axutil_hash_first(svc->op_action_map, env); hi; hi = axutil_hash_next(env, hi)) { axutil_hash_this(hi, &key, NULL, NULL); nc_tmp = nc_name; if(key) { axis2_char_t *search = NULL; axis2_bool_t match_start = AXIS2_TRUE; axis2_char_t *search_tmp = NULL; search = (axis2_char_t *)key; if(!axutil_strchr(search, '*')) { if(axutil_strstr(nc_tmp, search)) { axis2_char_t *comp_tmp = NULL; comp_tmp = axutil_strstr(nc_tmp, search); if(strlen(comp_tmp) == strlen(search)) { nc_tmp = (axis2_char_t *)key; is_matched = AXIS2_TRUE; break; } } continue; } if(search[0] == '*') { search++; if(!*search) { nc_tmp = (axis2_char_t *)key; is_matched = AXIS2_TRUE; break; } else if(axutil_strchr(search, '*')) { continue; } match_start = AXIS2_FALSE; } while(search && *search) { int length = 0; axis2_char_t *loc_tmp = NULL; if(search_tmp) { AXIS2_FREE(env->allocator, search_tmp); search_tmp = NULL; } loc_tmp = axutil_strchr(search, '*'); if(loc_tmp && *loc_tmp) { if(!loc_tmp[1]) { is_matched = AXIS2_TRUE; break; } length = (int)(loc_tmp - search); /* We are sure that the difference lies within the int range */ search_tmp = (axis2_char_t *)(AXIS2_MALLOC(env->allocator, sizeof(axis2_char_t) * (length + 1))); strncpy(search_tmp, search, length); search_tmp[length] = '\0'; } else if(axutil_strstr(nc_tmp, search)) { axis2_char_t *comp_tmp = NULL; comp_tmp = axutil_strstr(nc_tmp, search); if(strlen(comp_tmp) == strlen(search)) { nc_tmp = (axis2_char_t *)key; is_matched = AXIS2_TRUE; break; } break; } else { break; } if(search_tmp && axutil_strstr(nc_tmp, search_tmp)) { if(match_start && !(axutil_strncmp(nc_tmp, search, length) == 0)) { break; } else if(!match_start) { match_start = AXIS2_TRUE; } } else { break; } search += axutil_strlen(search_tmp) + 1; nc_tmp = axutil_strstr(nc_tmp, search_tmp) + axutil_strlen(search_tmp); } if(search_tmp) { AXIS2_FREE(env->allocator, search_tmp); search_tmp = NULL; } if(is_matched || !*search) { nc_tmp = (axis2_char_t *)key; is_matched = AXIS2_TRUE; break; } } } } if(!is_matched) { nc_tmp = nc_name; } op = axutil_hash_get(svc->op_alias_map, nc_tmp, AXIS2_HASH_KEY_STRING); if(op) { return op; } return (axis2_op_t *)axutil_hash_get(svc->op_action_map, nc_tmp, AXIS2_HASH_KEY_STRING); } AXIS2_EXTERN axutil_array_list_t *AXIS2_CALL axis2_svc_get_rest_op_list_with_method_and_location( const axis2_svc_t * svc, const axutil_env_t * env, const axis2_char_t * method, const axis2_char_t * location) { axutil_array_list_t *op_list = NULL; axis2_char_t *key = NULL; axis2_char_t *loc_str = NULL; axis2_char_t *loc_str_tmp = NULL; axis2_char_t *rindex = NULL; int plen; AXIS2_PARAM_CHECK(env->error, method, NULL); AXIS2_PARAM_CHECK(env->error, location, NULL); loc_str_tmp = (axis2_char_t *)location; /* Casted to facilitate loop */ if(loc_str_tmp[1] == '/') { loc_str_tmp++; } /* ignore any '/' at the beginning */ if(strchr(loc_str_tmp, '?')) { axis2_char_t *temp = NULL; temp = strchr(loc_str_tmp, '?'); temp[0] = '\0'; } /* ignore block after '?' */ do { axis2_char_t *temp = NULL; temp = strchr(loc_str_tmp, '{'); if(temp) { loc_str_tmp = temp; } else { loc_str_tmp += strlen(loc_str_tmp); break; } } while(loc_str_tmp[1] && loc_str_tmp[1] == '{'); loc_str = (axis2_char_t *)axutil_strmemdup(location, (loc_str_tmp - location), env); rindex = axutil_rindex(loc_str, '/'); if(rindex && *rindex) { loc_str_tmp = axutil_string_substring_ending_at(loc_str, (int)(rindex - loc_str)); /* We are sure that the difference lies within the int range */ } else { loc_str_tmp = loc_str; } plen = axutil_strlen(method) + axutil_strlen(loc_str_tmp) + 2; key = (axis2_char_t *)(AXIS2_MALLOC(env->allocator, sizeof(axis2_char_t) * plen)); sprintf(key, "%s:%s", method, loc_str_tmp); AXIS2_FREE(env->allocator, loc_str); op_list = (axutil_array_list_t *)axutil_hash_get(svc->op_rest_map, key, AXIS2_HASH_KEY_STRING); AXIS2_FREE(env->allocator, key); return op_list; } AXIS2_EXTERN axis2_op_t *AXIS2_CALL axis2_svc_get_op_with_name( const axis2_svc_t * svc, const axutil_env_t * env, const axis2_char_t * nc_name) { AXIS2_PARAM_CHECK(env->error, nc_name, NULL); return (axis2_op_t *)axutil_hash_get(svc->op_alias_map, nc_name, AXIS2_HASH_KEY_STRING); } AXIS2_EXTERN axutil_hash_t *AXIS2_CALL axis2_svc_get_all_ops( const axis2_svc_t * svc, const axutil_env_t * env) { return svc->op_alias_map; } AXIS2_EXTERN axis2_status_t AXIS2_CALL axis2_svc_set_parent( axis2_svc_t * svc, const axutil_env_t * env, axis2_svc_grp_t * svc_grp) { AXIS2_PARAM_CHECK(env->error, svc_grp, AXIS2_FAILURE); svc->parent = svc_grp; if(svc_grp) { axis2_desc_set_parent(svc->base, env, axis2_svc_grp_get_base(svc_grp, env)); } return AXIS2_SUCCESS; } AXIS2_EXTERN axis2_svc_grp_t *AXIS2_CALL axis2_svc_get_parent( const axis2_svc_t * svc, const axutil_env_t * env) { return svc->parent; } AXIS2_EXTERN axis2_status_t AXIS2_CALL axis2_svc_set_qname( axis2_svc_t * svc, const axutil_env_t * env, const axutil_qname_t * qname) { AXIS2_PARAM_CHECK(env->error, qname, AXIS2_FAILURE); if(svc->qname) { axutil_qname_free(svc->qname, env); } if(qname) { svc->qname = axutil_qname_clone((axutil_qname_t *)qname, env); } return AXIS2_SUCCESS; } AXIS2_EXTERN const axutil_qname_t *AXIS2_CALL axis2_svc_get_qname( const axis2_svc_t * svc, const axutil_env_t * env) { return svc->qname; } AXIS2_EXTERN axis2_status_t AXIS2_CALL axis2_svc_add_param( axis2_svc_t * svc, const axutil_env_t * env, axutil_param_t * param) { axis2_char_t *paramname = NULL; const axis2_char_t *svcname = axis2_svc_get_name(svc, env); AXIS2_PARAM_CHECK(env->error, param, AXIS2_FAILURE); paramname = axutil_param_get_name(param, env); if(axis2_svc_is_param_locked(svc, env, axutil_param_get_name(param, env))) { AXIS2_ERROR_SET(env->error, AXIS2_ERROR_PARAMETER_LOCKED_CANNOT_OVERRIDE, AXIS2_FAILURE); AXIS2_LOG_ERROR(env->log, AXIS2_LOG_SI, "Parameter %s is locked for service %s", paramname, svcname); return AXIS2_FAILURE; } return axutil_param_container_add_param(svc->param_container, env, param); } AXIS2_EXTERN axutil_param_t *AXIS2_CALL axis2_svc_get_param( const axis2_svc_t * svc, const axutil_env_t * env, const axis2_char_t * name) { axutil_param_t *param = NULL; AXIS2_PARAM_CHECK(env->error, name, NULL); param = axutil_param_container_get_param(svc->param_container, env, name); if(!param && svc->parent) { param = axis2_svc_grp_get_param(svc->parent, env, name); } return param; } AXIS2_EXTERN axis2_status_t AXIS2_CALL axis2_svc_remove_param( const axis2_svc_t *svc, const axutil_env_t *env, const axis2_char_t *param_name) { axis2_status_t status = AXIS2_FAILURE; status = axutil_param_container_delete_param(svc->param_container, env, param_name); return status; } AXIS2_EXTERN axutil_array_list_t *AXIS2_CALL axis2_svc_get_all_params( const axis2_svc_t * svc, const axutil_env_t * env) { return axutil_param_container_get_params(svc->param_container, env); } AXIS2_EXTERN axis2_bool_t AXIS2_CALL axis2_svc_is_param_locked( axis2_svc_t * svc, const axutil_env_t * env, const axis2_char_t * param_name) { axis2_bool_t locked = AXIS2_FALSE; axutil_param_t *param = NULL; axis2_svc_grp_t *parent = NULL; axis2_bool_t ret = AXIS2_FALSE; AXIS2_PARAM_CHECK(env->error, param_name, AXIS2_FALSE); /* Checking the locked value of parent */ parent = axis2_svc_get_parent(svc, env); if(parent) locked = axis2_svc_grp_is_param_locked(parent, env, param_name); if(parent && locked) { return AXIS2_TRUE; } param = axis2_svc_get_param(svc, env, param_name); if(param) { ret = axutil_param_is_locked(param, env); } return ret; } AXIS2_EXTERN axis2_status_t AXIS2_CALL axis2_svc_engage_module( axis2_svc_t * svc, const axutil_env_t * env, axis2_module_desc_t * module_desc, axis2_conf_t * conf) { axis2_phase_resolver_t *phase_resolver = NULL; axis2_status_t status = AXIS2_FAILURE; const axis2_char_t *svcname = NULL; AXIS2_LOG_TRACE(env->log, AXIS2_LOG_SI, "Entry:axis2_svc_engage_module"); AXIS2_PARAM_CHECK(env->error, module_desc, AXIS2_FAILURE); AXIS2_PARAM_CHECK(env->error, conf, AXIS2_FAILURE); svcname = axis2_svc_get_name(svc, env); phase_resolver = axis2_phase_resolver_create_with_config(env, conf); if(!phase_resolver) { AXIS2_LOG_ERROR(env->log, AXIS2_LOG_SI, "Creating phase resolver failed for service %s", svcname); return AXIS2_FAILURE; } status = axis2_phase_resolver_engage_module_to_svc(phase_resolver, env, svc, module_desc); if(status) { const axutil_qname_t *qname = NULL; status = axutil_array_list_add(svc->engaged_module_list, env, module_desc); qname = axis2_module_desc_get_qname(module_desc, env); axis2_svc_add_module_qname(svc, env, qname); } if(phase_resolver) { axis2_phase_resolver_free(phase_resolver, env); } AXIS2_LOG_TRACE(env->log, AXIS2_LOG_SI, "Exit:axis2_svc_engage_module"); return status; } AXIS2_EXTERN axis2_bool_t AXIS2_CALL axis2_svc_is_module_engaged( axis2_svc_t * svc, const axutil_env_t * env, axutil_qname_t * module_qname) { int i = 0, size = 0; AXIS2_LOG_TRACE(env->log, AXIS2_LOG_SI, "Entry:axis2_svc_is_module_engaged"); size = axutil_array_list_size(svc->engaged_module_list, env); for(i = 0; i < size; i++) { const axutil_qname_t *module_qname_l = NULL; axis2_module_desc_t *module_desc_l = NULL; module_desc_l = (axis2_module_desc_t *)axutil_array_list_get(svc->engaged_module_list, env, i); module_qname_l = axis2_module_desc_get_qname(module_desc_l, env); if(axutil_qname_equals(module_qname, env, module_qname_l)) { return AXIS2_TRUE; } } AXIS2_LOG_TRACE(env->log, AXIS2_LOG_SI, "Exit:axis2_svc_is_module_engaged"); return AXIS2_FALSE; } AXIS2_EXTERN axutil_array_list_t *AXIS2_CALL axis2_svc_get_engaged_module_list( const axis2_svc_t * svc, const axutil_env_t * env) { return svc->engaged_module_list; } AXIS2_EXTERN axis2_status_t AXIS2_CALL axis2_svc_disengage_module( axis2_svc_t * svc, const axutil_env_t * env, axis2_module_desc_t * module_desc, axis2_conf_t * conf) { axis2_phase_resolver_t *phase_resolver = NULL; axis2_status_t status = AXIS2_FAILURE; const axis2_char_t *svcname = NULL; AXIS2_PARAM_CHECK(env->error, module_desc, AXIS2_FAILURE); AXIS2_PARAM_CHECK(env->error, conf, AXIS2_FAILURE); svcname = axis2_svc_get_name(svc, env); phase_resolver = axis2_phase_resolver_create_with_config(env, conf); if(!phase_resolver) { AXIS2_LOG_ERROR(env->log, AXIS2_LOG_SI, "Creating phase resolver failed for service %s", svcname); return AXIS2_FAILURE; } status = axis2_phase_resolver_disengage_module_from_svc(phase_resolver, env, svc, module_desc); if(status == AXIS2_SUCCESS) { /** Remove this module from the engaged modules list */ const axutil_qname_t *mod_qname = NULL; int i = 0, size = 0; mod_qname = axis2_module_desc_get_qname(module_desc, env); size = axutil_array_list_size(svc->engaged_module_list, env); for(i = 0; i < size; i++) { const axutil_qname_t *module_qname_l = NULL; axis2_module_desc_t *module_desc_l = NULL; module_desc_l = (axis2_module_desc_t *)axutil_array_list_get(svc->engaged_module_list, env, i); module_qname_l = axis2_module_desc_get_qname(module_desc_l, env); if(axutil_qname_equals(mod_qname, env, module_qname_l)) { axutil_array_list_remove(svc->engaged_module_list, env, i); break; } } } axis2_phase_resolver_free(phase_resolver, env); return status; } /** * Here we extract all operations defined in module.xml and built execution * chains for them by calling axis2_phase_resolver_build_execution_chains_for_module_op() * function. Within that function handlers of the modules defined for that * operation are added to module operation chains appropriately. */ AXIS2_EXTERN axis2_status_t AXIS2_CALL axis2_svc_add_module_ops( axis2_svc_t * svc, const axutil_env_t * env, axis2_module_desc_t * module_desc, axis2_conf_t * conf) { axutil_hash_t *map = NULL; axutil_hash_index_t *index = NULL; axis2_phase_resolver_t *phase_resolver = NULL; axis2_op_t *op_desc = NULL; axis2_status_t status = AXIS2_FAILURE; const axis2_char_t *svcname = NULL; axis2_char_t *modname = NULL; axis2_char_t *opname = NULL; AXIS2_LOG_TRACE(env->log, AXIS2_LOG_SI, "Entry:axis2_svc_add_module_ops"); AXIS2_PARAM_CHECK(env->error, module_desc, AXIS2_FAILURE); AXIS2_PARAM_CHECK(env->error, conf, AXIS2_FAILURE); svcname = axis2_svc_get_name(svc, env); modname = axutil_qname_get_localpart(axis2_module_desc_get_qname(module_desc, env), env); map = axis2_module_desc_get_all_ops(module_desc, env); phase_resolver = axis2_phase_resolver_create_with_config_and_svc(env, conf, svc); if(!phase_resolver) { AXIS2_LOG_ERROR(env->log, AXIS2_LOG_SI, "Creating phase resolver failed for service %s", svcname); return AXIS2_FAILURE; } for(index = axutil_hash_first(map, env); index; index = axutil_hash_next(env, index)) { void *v = NULL; axutil_hash_this(index, NULL, NULL, &v); op_desc = (axis2_op_t *)v; opname = axutil_qname_get_localpart(axis2_op_get_qname(op_desc, env), env); status = axis2_phase_resolver_build_execution_chains_for_module_op(phase_resolver, env, op_desc); if(AXIS2_SUCCESS != status) { if(phase_resolver) { axis2_phase_resolver_free(phase_resolver, env); } AXIS2_LOG_ERROR(env->log, AXIS2_LOG_SI, "Builidng module operation %s failed for module %s", opname, modname); return status; } status = axis2_svc_add_op(svc, env, op_desc); if(AXIS2_SUCCESS != status) { if(phase_resolver) { axis2_phase_resolver_free(phase_resolver, env); } AXIS2_LOG_ERROR(env->log, AXIS2_LOG_SI, "Adding operation %s to service %s failed", opname, svcname); return status; } } if(phase_resolver) { axis2_phase_resolver_free(phase_resolver, env); } AXIS2_LOG_TRACE(env->log, AXIS2_LOG_SI, "Exit:axis2_svc_add_module_ops"); return AXIS2_SUCCESS; } AXIS2_EXTERN const axis2_char_t *AXIS2_CALL axis2_svc_get_name( const axis2_svc_t * svc, const axutil_env_t * env) { if(svc->qname) { return axutil_qname_get_localpart(svc->qname, env); } return NULL; } AXIS2_EXTERN axis2_status_t AXIS2_CALL axis2_svc_set_name( axis2_svc_t * svc, const axutil_env_t * env, const axis2_char_t * axis_svc_name) { AXIS2_PARAM_CHECK(env->error, axis_svc_name, AXIS2_FAILURE); if(svc->axis_svc_name) { AXIS2_FREE(env->allocator, svc->axis_svc_name); svc->axis_svc_name = NULL; } svc->axis_svc_name = axutil_strdup(env, axis_svc_name); if(!svc->axis_svc_name) { AXIS2_ERROR_SET(env->error, AXIS2_ERROR_NO_MEMORY, AXIS2_FAILURE); AXIS2_LOG_ERROR(env->log, AXIS2_LOG_SI, "No memory"); return AXIS2_FAILURE; } return AXIS2_SUCCESS; } AXIS2_EXTERN axis2_status_t AXIS2_CALL axis2_svc_set_last_update( axis2_svc_t * svc, const axutil_env_t * env) { return AXIS2_SUCCESS; } AXIS2_EXTERN long AXIS2_CALL axis2_svc_get_last_update( const axis2_svc_t * svc, const axutil_env_t * env) { return svc->last_update; } AXIS2_EXTERN const axis2_char_t *AXIS2_CALL axis2_svc_get_file_name( const axis2_svc_t * svc, const axutil_env_t * env) { return svc->filename; } AXIS2_EXTERN axis2_status_t AXIS2_CALL axis2_svc_set_file_name( axis2_svc_t * svc, const axutil_env_t * env, const axis2_char_t * filename) { AXIS2_PARAM_CHECK(env->error, filename, AXIS2_FAILURE); if(svc->filename) { AXIS2_FREE(env->allocator, svc->filename); svc->filename = NULL; } svc->filename = (axis2_char_t *)axutil_strdup(env, filename); if(!svc->filename) { AXIS2_ERROR_SET(env->error, AXIS2_ERROR_NO_MEMORY, AXIS2_FAILURE); AXIS2_LOG_ERROR(env->log, AXIS2_LOG_SI, "No memory"); return AXIS2_FAILURE; } return AXIS2_SUCCESS; } AXIS2_EXTERN const axis2_char_t *AXIS2_CALL axis2_svc_get_svc_desc( const axis2_svc_t * svc, const axutil_env_t * env) { return svc->svc_desc; } AXIS2_EXTERN axis2_status_t AXIS2_CALL axis2_svc_set_svc_desc( axis2_svc_t * svc, const axutil_env_t * env, const axis2_char_t * svc_desc) { AXIS2_PARAM_CHECK(env->error, svc_desc, AXIS2_FAILURE); if(svc->svc_desc) { AXIS2_FREE(env->allocator, svc->svc_desc); svc->svc_desc = NULL; } svc->svc_desc = (axis2_char_t *)axutil_strdup(env, svc_desc); if(!svc->svc_desc) { AXIS2_ERROR_SET(env->error, AXIS2_ERROR_NO_MEMORY, AXIS2_FAILURE); AXIS2_LOG_ERROR(env->log, AXIS2_LOG_SI, "No memory"); return AXIS2_FAILURE; } return AXIS2_SUCCESS; } AXIS2_EXTERN axis2_status_t AXIS2_CALL axis2_svc_add_mapping( axis2_svc_t * svc, const axutil_env_t * env, const axis2_char_t * mapping_key, axis2_op_t * op_desc) { AXIS2_PARAM_CHECK(env->error, mapping_key, AXIS2_FAILURE); AXIS2_PARAM_CHECK(env->error, op_desc, AXIS2_FAILURE); axutil_hash_set(svc->op_action_map, axutil_strdup(env, mapping_key), AXIS2_HASH_KEY_STRING, op_desc); return AXIS2_SUCCESS; } AXIS2_EXTERN axis2_status_t AXIS2_CALL axis2_svc_add_rest_mapping( axis2_svc_t * svc, const axutil_env_t * env, const axis2_char_t * method, const axis2_char_t * location, axis2_op_t * op_desc) { axis2_char_t *mapping_url = NULL; int key_len = 0; axis2_char_t* question_char = NULL; axis2_char_t* local_location_str = NULL; axis2_status_t status = AXIS2_SUCCESS; local_location_str = (axis2_char_t *)location; /* Casted to facilitate loop */ /* skip the beginning '/' */ if(*local_location_str == '/') { local_location_str++; } question_char = axutil_strchr(local_location_str, '?'); if(question_char) { *question_char = '\0'; } key_len = axutil_strlen(method) + axutil_strlen(local_location_str) + 2; mapping_url = (axis2_char_t *)(AXIS2_MALLOC(env->allocator, sizeof(axis2_char_t) * key_len)); if(!mapping_url) { AXIS2_ERROR_SET(env->error, AXIS2_ERROR_NO_MEMORY, AXIS2_FAILURE); AXIS2_LOG_ERROR(env->log, AXIS2_LOG_SI, "No memory. Cannot create the rest mapping url"); return AXIS2_FAILURE; } sprintf(mapping_url, "%s:%s", method, local_location_str); status = axis2_core_utils_prepare_rest_mapping(env, mapping_url, svc->op_rest_map, op_desc); if(mapping_url) { AXIS2_FREE(env->allocator, mapping_url); } /* restore the question character */ if(question_char) { *question_char = '?'; } return status; } AXIS2_EXTERN axis2_status_t AXIS2_CALL axis2_svc_add_module_qname( axis2_svc_t * svc, const axutil_env_t * env, const axutil_qname_t * module_qname) { axutil_qname_t *qmodule_qname_l = NULL; AXIS2_PARAM_CHECK(env->error, module_qname, AXIS2_FAILURE); qmodule_qname_l = axutil_qname_clone((axutil_qname_t *)module_qname, env); return axutil_array_list_add(svc->module_list, env, qmodule_qname_l); } AXIS2_EXTERN axutil_array_list_t *AXIS2_CALL axis2_svc_get_all_module_qnames( const axis2_svc_t * svc, const axutil_env_t * env) { return svc->module_list; } AXIS2_EXTERN const axis2_char_t *AXIS2_CALL axis2_svc_get_target_ns( const axis2_svc_t * svc, const axutil_env_t * env) { return svc->target_ns; } AXIS2_EXTERN axis2_status_t AXIS2_CALL axis2_svc_set_target_ns( axis2_svc_t * svc, const axutil_env_t * env, const axis2_char_t * ns) { AXIS2_PARAM_CHECK(env->error, ns, AXIS2_FAILURE); if(svc->target_ns) { AXIS2_FREE(env->allocator, svc->target_ns); svc->target_ns = NULL; } svc->target_ns = axutil_strdup(env, ns); return AXIS2_SUCCESS; } AXIS2_EXTERN const axis2_char_t *AXIS2_CALL axis2_svc_get_target_ns_prefix( const axis2_svc_t * svc, const axutil_env_t * env) { return svc->target_ns_prefix; } AXIS2_EXTERN axis2_status_t AXIS2_CALL axis2_svc_set_target_ns_prefix( axis2_svc_t * svc, const axutil_env_t * env, const axis2_char_t * prefix) { AXIS2_PARAM_CHECK(env->error, prefix, AXIS2_FAILURE); if(svc->target_ns_prefix) { AXIS2_FREE(env->allocator, svc->target_ns_prefix); svc->target_ns_prefix = NULL; } svc->target_ns_prefix = axutil_strdup(env, prefix); return AXIS2_SUCCESS; } AXIS2_EXTERN axutil_hash_t *AXIS2_CALL axis2_svc_get_ns_map( const axis2_svc_t * svc, const axutil_env_t * env) { return svc->ns_map; } AXIS2_EXTERN axis2_status_t AXIS2_CALL axis2_svc_set_ns_map( axis2_svc_t * svc, const axutil_env_t * env, axutil_hash_t * ns_map) { axutil_hash_index_t *hi = NULL; AXIS2_PARAM_CHECK(env->error, ns_map, AXIS2_FAILURE); if(svc->ns_map) { for(hi = axutil_hash_first(svc->ns_map, env); hi; hi = axutil_hash_next(env, hi)) { void *value = NULL; void *key = NULL; axutil_hash_this(hi, (const void **)&key, NULL, (void **)&value); if(key) { AXIS2_FREE(env->allocator, key); key = NULL; } if(value) { AXIS2_FREE(env->allocator, value); value = NULL; } } axutil_hash_free(svc->ns_map, env); } svc->ns_map = ns_map; return AXIS2_SUCCESS; } AXIS2_EXTERN axutil_hash_t *AXIS2_CALL axis2_svc_swap_mapping_table( axis2_svc_t * svc, const axutil_env_t * env, axutil_hash_t * orig_table) { axutil_hash_t *new_table = NULL; axutil_hash_index_t *hi = NULL; AXIS2_PARAM_CHECK(env->error, orig_table, NULL); new_table = axutil_hash_make(env); for(hi = axutil_hash_first(orig_table, env); env; hi = axutil_hash_next(env, hi)) { void *value = NULL; void *key = NULL; axutil_hash_this(hi, (const void **)&key, NULL, (void **)&value); axutil_hash_set(new_table, value, AXIS2_HASH_KEY_STRING, key); } return new_table; } AXIS2_EXTERN void *AXIS2_CALL axis2_svc_get_impl_class( const axis2_svc_t * svc, const axutil_env_t * env) { return svc->impl_class; } AXIS2_EXTERN axis2_status_t AXIS2_CALL axis2_svc_set_impl_class( axis2_svc_t * svc, const axutil_env_t * env, void *impl_class) { svc->impl_class = impl_class; return AXIS2_SUCCESS; } AXIS2_EXTERN axutil_param_container_t *AXIS2_CALL axis2_svc_get_param_container( const axis2_svc_t * svc, const axutil_env_t * env) { return svc->param_container; } AXIS2_EXTERN axis2_flow_container_t *AXIS2_CALL axis2_svc_get_flow_container( const axis2_svc_t * svc, const axutil_env_t * env) { return svc->flow_container; } AXIS2_EXTERN const axis2_char_t *AXIS2_CALL axis2_svc_get_svc_wsdl_path( const axis2_svc_t * svc, const axutil_env_t * env) { return svc->wsdl_path; } AXIS2_EXTERN axis2_status_t AXIS2_CALL axis2_svc_set_svc_wsdl_path( axis2_svc_t * svc, const axutil_env_t * env, const axis2_char_t * wsdl_path) { AXIS2_PARAM_CHECK(env->error, wsdl_path, AXIS2_FAILURE); svc->wsdl_path = (axis2_char_t *)axutil_strdup(env, wsdl_path); return AXIS2_SUCCESS; } AXIS2_EXTERN const axis2_char_t *AXIS2_CALL axis2_svc_get_svc_folder_path( const axis2_svc_t * svc, const axutil_env_t * env) { return svc->folder_path; } AXIS2_EXTERN axis2_status_t AXIS2_CALL axis2_svc_set_svc_folder_path( axis2_svc_t * svc, const axutil_env_t * env, const axis2_char_t * folder_path) { AXIS2_PARAM_CHECK(env->error, folder_path, AXIS2_FAILURE); svc->folder_path = (axis2_char_t *)axutil_strdup(env, folder_path); return AXIS2_SUCCESS; } AXIS2_EXTERN axis2_desc_t *AXIS2_CALL axis2_svc_get_base( const axis2_svc_t * svc, const axutil_env_t * env) { return svc->base; } AXIS2_EXTERN axutil_thread_mutex_t * AXIS2_CALL axis2_svc_get_mutex( const axis2_svc_t * svc, const axutil_env_t * env) { return svc->mutex; } AXIS2_EXTERN axutil_hash_t *AXIS2_CALL axis2_svc_get_rest_map( const axis2_svc_t * svc, const axutil_env_t * env) { return svc->op_rest_map; }