Example #1
0
/** 
 * Do deserialization over complex schema types and move to the next element
 * @param $current_child is the relevent xml node to parse, and 
 *                   move the current_child to the next child
 * @param $sig_param_node the sig model for the param
 *
 * @param $classmap the classmap passed by the user
 * @return the result complex type value.
 */
function wsf_deserialize_complex_types(&$current_child, DomNode $sig_param_node, $classmap, $cid2cont_type, $cid2attachments)
{
    $ret_val = NULL;
    $target_namespace = NULL;
    $min_occurs = 1;
    $max_occurs = 1;
    $sig_param_attris = $sig_param_node->attributes;
    $param_type = NULL;
    $param_name = NULL;
    $is_attribute = FALSE;
    $nillable = FALSE;
    if ($sig_param_attris->getNamedItem(WSF_NAME)) {
        $param_name = $sig_param_attris->getNamedItem(WSF_NAME)->value;
    }
    if ($sig_param_attris->getNamedItem(WSF_TARGETNAMESPACE)) {
        $target_namespace = $sig_param_attris->getNamedItem(WSF_TARGETNAMESPACE)->value;
    }
    if ($sig_param_attris->getNamedItem(WSF_MIN_OCCURS)) {
        $min_occurs = $sig_param_attris->getNamedItem(WSF_MIN_OCCURS)->value;
    }
    if ($sig_param_attris->getNamedItem(WSF_MAX_OCCURS)) {
        $max_occurs = $sig_param_attris->getNamedItem(WSF_MAX_OCCURS)->value;
    }
    if ($sig_param_attris->getNamedItem(WSF_TYPE)) {
        $param_type = $sig_param_attris->getNamedItem(WSF_TYPE)->value;
    }
    if ($sig_param_attris->getNamedItem(WSF_XSD_NILLABLE) && ($sig_param_attris->getNamedItem(WSF_XSD_NILLABLE)->value = "true")) {
        $nillable = TRUE;
    }
    if ($sig_param_attris->getNamedItem(WSF_ATTRIBUTE) && $sig_param_attris->getNamedItem(WSF_ATTRIBUTE)->value == "yes") {
        $is_attribute = TRUE;
    }
    if ($max_occurs > 1 || $max_occurs == "unbounded") {
        $i = 0;
        $tmp_array = array();
        while ($current_child !== NULL && $current_child->localName == $param_name) {
            if ($sig_param_node->hasChildNodes()) {
                if ($classmap) {
                    $converted_value = wsf_parse_payload_for_class_map($current_child, $sig_param_node, $param_type, $classmap, $cid2cont_type, $cid2attachments);
                } else {
                    $converted_value = wsf_parse_payload_for_array($current_child, $sig_param_node, $cid2cont_type, $cid2attachments);
                }
            } else {
                if ($classmap) {
                    $converted_value = wsf_parse_payload_for_unknown_class_map($current_child, $param_type, $classmap);
                } else {
                    $converted_value = wsf_parse_payload_for_unknown_array($current_child);
                }
            }
            if (!$current_child->firstChild && !$current_child->hasAttributes()) {
                // handling nil element
                $converted_value = wsf_wsdl_deserialize_string_value($param_type, "", $sig_param_node, $current_child);
            }
            $tmp_array[$i++] = $converted_value;
            $current_child = $current_child->nextSibling;
            while ($current_child != NULL && $current_child->nodeType != XML_ELEMENT_NODE) {
                $current_child = $current_child->nextSibling;
            }
        }
        $ret_val = $tmp_array;
    } else {
        if ($sig_param_node->hasChildNodes()) {
            if ($classmap) {
                $converted_value = wsf_parse_payload_for_class_map($current_child, $sig_param_node, $param_type, $classmap, $cid2cont_type, $cid2attachments);
            } else {
                $converted_value = wsf_parse_payload_for_array($current_child, $sig_param_node, $cid2cont_type, $cid2attachments);
            }
        } else {
            if ($classmap) {
                $converted_value = wsf_parse_payload_for_unknown_class_map($current_child, $param_type, $classmap);
            } else {
                $converted_value = wsf_parse_payload_for_unknown_array($current_child);
            }
        }
        if (!$current_child->firstChild && !$current_child->hasAttributes()) {
            // handling nil element
            $converted_value = wsf_wsdl_deserialize_string_value($param_type, "", $sig_param_node, $current_child);
        }
        $ret_val = $converted_value;
        $current_child = $current_child->nextSibling;
        while ($current_child != NULL && $current_child->nodeType != XML_ELEMENT_NODE) {
            $current_child = $current_child->nextSibling;
        }
    }
    return $ret_val;
}
Example #2
0
/**
 * service invoke function
 */
function wsf_serivce_invoke_function($operation_node, $function_name, $class_name, $class_args, $soap_body_node, $header_node, $classmap, $mtom_on, $cid2cont_type, $cid2attachments)
{
    require_once 'wsf_wsdl_consts.php';
    require_once 'wsf_wsdl_util.php';
    require_once 'wsf_wsdl_deserialization.php';
    $sig_node = NULL;
    $binding_details_node = NULL;
    if ($operation_node) {
        foreach ($operation_node->childNodes as $operation_child) {
            if ($operation_child->tagName == WSF_SIGNATURE) {
                $sig_node = $operation_child;
            }
            if ($operation_child->tagName == WSF_BINDINDG_DETAILS) {
                $binding_details_node = $operation_child;
            }
        }
    }
    $is_doc = TRUE;
    //currently we only support doc-lit style parsing..
    $is_wrapper = FALSE;
    $params_node = NULL;
    $is_direct_list = FALSE;
    if ($sig_node) {
        $params_node = $sig_node->firstChild;
        if ($params_node && $params_node->localName == WSF_PARAMS) {
            if ($params_node->hasAttributes()) {
                /* Wrapper element of the request operation */
                $sig_attrs = $params_node->attributes;
                if ($sig_attrs->getNamedItem(WSF_WRAPPER_ELEMENT)) {
                    $ele_name = $sig_attrs->getNamedItem(WSF_WRAPPER_ELEMENT)->value;
                }
                if ($sig_attrs->getNamedItem(WSF_WRAPPER_ELEMENT_NS)) {
                    $ele_ns = $sig_attrs->getNamedItem(WSF_WRAPPER_ELEMENT_NS)->value;
                }
                $is_wrapper = TRUE;
            } else {
                /* No wrapper element in the request */
                $ele_ns = NULL;
                $ele_name = NULL;
                /* check for the only param target-namespace */
                $only_param = $params_node->firstChild;
                $sig_attrs = $only_param->attributes;
                if ($sig_attrs->getNamedItem(WSF_TARGETNAMESPACE)) {
                    $ele_ns = $sig_attrs->getNamedItem(WSF_TARGETNAMESPACE)->value;
                }
                if ($sig_attrs->getNamedItem(WSF_NAME)) {
                    $ele_name = $sig_attrs->getNamedItem(WSF_NAME)->value;
                }
                if ($sig_attrs->getNamedItem(WSF_LIST)) {
                    $is_direct_list = $sig_attrs->getNamedItem(WSF_LIST)->value;
                }
            }
        }
    }
    if (!$soap_body_node) {
        ws_log_write(__FILE__, __LINE__, WSF_LOG_DEBUG, "soap_body not found");
    }
    // parsing input headers
    $header_params = array();
    $output_headers = array();
    if ($header_node) {
        $header_first_child = $header_node->firstChild;
        $output_index = 0;
        if ($binding_details_node) {
            $binding_details_childs = $binding_details_node->childNodes;
            foreach ($binding_details_childs as $binding_details_child) {
                if ($binding_details_child->nodeType == XML_ELEMENT_NODE && $binding_details_child->nodeName == WSF_SOAPHEADER && $binding_details_child->attributes->getNamedItem(WSF_HEADER_FOR_ATTRIBUTE)) {
                    if ($binding_details_child->attributes->getNamedItem(WSF_HEADER_FOR_ATTRIBUTE)->value == WSF_WSDL_INPUT) {
                        //so this is the next input element..
                        $sig_attrs = $binding_details_child->attributes;
                        if ($sig_attrs->getNamedItem(WSF_TYPE)) {
                            $ele_name = $sig_attrs->getNamedItem(WSF_TYPE)->value;
                        }
                        if ($sig_attrs->getNamedItem(WSF_TYPE_NAMESPACE)) {
                            $ele_ns = $sig_attrs->getNamedItem(WSF_TYPE_NAMESPACE)->value;
                        }
                        // for the starting sig we have to go for the header node name we want
                        //go to the next header
                        if ($header_first_child) {
                            $header_child = $header_first_child;
                            while ($header_child && ($header_child->nodeType == XML_TEXT_NODE || !($header_child->localName == $ele_name && $header_child->namespaceURI == $ele_ns))) {
                                $header_child = $header_child->nextSibling;
                            }
                        }
                        if ($header_child) {
                            $header_sig = $binding_details_child->firstChild;
                            if ($classmap != NULL && !empty($classmap)) {
                                ws_log_write(__FILE__, __LINE__, WSF_LOG_DEBUG, "starting to parse header {$ele_name} as a classmap");
                                $new_param = wsf_parse_payload_for_class_map($header_child, $header_sig, $ele_name, $classmap, $cid2cont_type, $cid2attachments);
                                ws_log_write(__FILE__, __LINE__, WSF_LOG_DEBUG, "parsed_pram " . print_r($new_param, TRUE) . " as a classmap");
                            } else {
                                ws_log_write(__FILE__, __LINE__, WSF_LOG_DEBUG, "starting to parse header {$ele_name} as an array");
                                $new_param = wsf_parse_payload_for_array($header_child, $header_sig, $cid2cont_type, $cid2attachments);
                            }
                            $header_params[] = $new_param;
                        } else {
                            //if header child doesn't exist better check whether it is an requeired header
                            if ($sig_attrs && $sig_attrs->getNamedItem(WSF_REQUIRED) && $sig_attrs->getNamedItem(WSF_REQUIRED)->value == "true") {
                                //throwing faults saying it is required
                                throw new WSFault("Sender", "Requried header {$ele_name}|{$ele_ns} missing");
                            }
                        }
                    } else {
                        if ($binding_details_child->attributes->getNamedItem(WSF_HEADER_FOR_ATTRIBUTE)->value == WSF_WSDL_OUTPUT) {
                            $output_headers[$output_index] = array();
                            //to retrive later
                            $header_params[] =& $output_headers[$output_index];
                            //to feed to the user operation
                            $output_index++;
                        }
                    }
                }
            }
        }
    }
    //parsing the pyalod
    $op_param_values = array();
    if ($classmap != NULL && !empty($classmap)) {
        if ($soap_body_node) {
            ws_log_write(__FILE__, __LINE__, WSF_LOG_DEBUG, "starting to parse payload as a classmap");
            $op_param_values = wsf_parse_payload_for_class_map($soap_body_node, $params_node, $ele_name, $classmap, $cid2cont_type, $cid2attachments);
        }
        $arg_array = array_merge(array($op_param_values), $header_params);
    } else {
        if ($soap_body_node) {
            ws_log_write(__FILE__, __LINE__, WSF_LOG_DEBUG, "starting to parse payload as an array");
            $op_param_values = wsf_parse_payload_for_array($soap_body_node, $params_node, $cid2cont_type, $cid2attachments);
            if (!is_array($op_param_values) || $is_direct_list) {
                // this can happens when returning simple types
                $op_param_values = array($op_param_values);
            }
        }
        $arg_array = array_merge($op_param_values, $header_params);
    }
    ws_log_write(__FILE__, __LINE__, WSF_LOG_DEBUG, print_r($arg_array, TRUE));
    if ($class_name != NULL) {
        // First call the constructor
        $class = new ReflectionClass($class_name);
        if ($class) {
            if ($class_args && is_array($class_args)) {
                $class_inst = $class->newInstanceArgs($class_args);
            } else {
                $class_inst = $class->newInstanceArgs(array());
            }
            // Then the user method
            $method = $class->getMethod($function_name);
            if ($classmap != NULL && !empty($classmap) || $is_direct_list) {
                // for direct lists we follow same api as classmap
                $response_value = $method->invokeArgs($class_inst, $arg_array);
            } else {
                $response_value = $method->invokeArgs($class_inst, $arg_array);
            }
        } else {
            ws_log_write(__FILE__, __LINE__, WSF_LOG_ERROR, "class : {$class_name} doesn't exists");
        }
    } else {
        if ($classmap != NULL && !empty($classmap) || $is_direct_list) {
            // for direct lists we follow same api as classmap
            $response_value = call_user_func_array($function_name, $arg_array);
        } else {
            $response_value = call_user_func_array($function_name, $arg_array);
        }
    }
    $attachment_map = array();
    $response_payload_string = wsf_wsdl_create_response_payload($response_value, $sig_node, $mtom_on, $attachment_map, $classmap);
    $output_header_string = wsf_wsdl_create_response_headers($binding_details_node, $output_headers, $mtom_on, $attachment_map, $classmap);
    return array(WSF_RESPONSE_PAYLOAD => $response_payload_string, WSF_OUTPUT_HEADERS => $output_header_string, WSF_ATTACHMENT_MAP => $attachment_map);
}
Example #3
0
/**
 * Processes and validate response message and assign values to class map.
 * @param DomDocument $payload_dom response payload
 * @param DomDocument $header_dom response header, can be NULL
 * @param DomDocument $operation_sig_dom operation sig model
 * @param array $response_parameters array of response parameters
 * @return mixed an object, an array or a simple type in line with the 
 * expected format of the response
 */
function wsf_client_response_and_validate(DomDocument $payload_dom, $header_dom, DomDocument $operation_sig_dom, $response_parameters, $mtom_on = FALSE)
{
    require_once 'wsf_wsdl_consts.php';
    require_once 'wsf_wsdl_util.php';
    require_once 'wsf_wsdl_deserialization.php';
    $payload_node = $payload_dom->documentElement;
    $operation_sig_node = $operation_sig_dom->documentElement;
    $binding_details_node = NULL;
    $sig_method = NULL;
    //extracting out the sig_method from the operation sig node
    if ($operation_sig_node) {
        foreach ($operation_sig_node->childNodes as $operation_sig_child) {
            if ($operation_sig_child->tagName == WSF_SIGNATURE) {
                $sig_method = $operation_sig_child;
            }
            if ($operation_sig_child->tagName == WSF_BINDINDG_DETAILS) {
                $binding_details_node = $operation_sig_child;
            }
        }
    }
    $ele_ns = NULL;
    $is_wrapper = FALSE;
    if ($sig_method) {
        $returns_node = $sig_method->firstChild;
        while ($returns_node && $returns_node->localName != WSF_RETURNS) {
            $returns_node = $returns_node->nextSibling;
        }
        if ($returns_node) {
            if ($returns_node->hasAttributes()) {
                /* Wrapper element of the request operation */
                $sig_attrs = $returns_node->attributes;
                $ele_name = NULL;
                $ele_ns = NULL;
                if ($sig_attrs->getNamedItem(WSF_WRAPPER_ELEMENT)) {
                    $ele_name = $sig_attrs->getNamedItem(WSF_WRAPPER_ELEMENT)->value;
                }
                if ($sig_attrs->getNamedItem(WSF_WRAPPER_ELEMENT_NS)) {
                    $ele_ns = $sig_attrs->getNamedItem(WSF_WRAPPER_ELEMENT_NS)->value;
                }
                $is_wrapper = TRUE;
            } else {
                /* No wrapper element in the request */
                $ele_ns = NULL;
                $ele_name = NULL;
                /* check for the only param target-namespace */
                $only_param = $returns_node->firstChild;
                $sig_attrs = $only_param->attributes;
                if ($sig_attrs->getNamedItem(WSF_TARGETNAMESPACE)) {
                    $ele_ns = $sig_attrs->getNamedItem(WSF_TARGETNAMESPACE)->value;
                }
                if ($sig_attrs->getNamedItem(WSF_NAME)) {
                    $ele_name = $sig_attrs->getNamedItem(WSF_NAME)->value;
                }
            }
        }
    }
    /** get SOAP body DOM tree to compare with Sig model */
    if (!$payload_node) {
        error_log("soap_body not found", 0);
    }
    $classmap = NULL;
    $cid2cont_type = array();
    $cid2attachments = array();
    if (array_key_exists(WSF_CLASSMAP, $response_parameters)) {
        $classmap = $response_parameters[WSF_CLASSMAP];
    }
    if (array_key_exists("attachments", $response_parameters)) {
        $cid2attachments = $response_parameters["attachments"];
    }
    if (array_key_exists("cid2contentType", $response_parameters)) {
        $cid2cont_type = $response_parameters["cid2contentType"];
    }
    $op_param_values = array();
    if ($classmap !== NULL) {
        $op_param_values = wsf_parse_payload_for_class_map($payload_node, $returns_node, $ele_name, $classmap, $cid2cont_type, $cid2attachments);
    } else {
        $op_param_values = wsf_parse_payload_for_array($payload_node, $returns_node, $cid2cont_type, $cid2attachments);
    }
    $header_node = NULL;
    if ($header_dom) {
        $header_node = $header_dom->documentElement;
    }
    $header_params = array();
    if ($header_node) {
        $header_first_child = $header_node->firstChild;
        $output_index = 0;
        if ($binding_details_node) {
            $binding_details_childs = $binding_details_node->childNodes;
            foreach ($binding_details_childs as $binding_details_child) {
                if ($binding_details_child->nodeType == XML_ELEMENT_NODE && $binding_details_child->nodeName == WSF_SOAPHEADER && $binding_details_child->attributes->getNamedItem(WSF_HEADER_FOR_ATTRIBUTE)) {
                    if ($binding_details_child->attributes->getNamedItem(WSF_HEADER_FOR_ATTRIBUTE)->value == WSF_WSDL_OUTPUT) {
                        //so this is the next input element..
                        $sig_attrs = $binding_details_child->attributes;
                        if ($sig_attrs->getNamedItem(WSF_TYPE)) {
                            $ele_name = $sig_attrs->getNamedItem(WSF_TYPE)->value;
                        }
                        if ($sig_attrs->getNamedItem(WSF_TYPE_NAMESPACE)) {
                            $ele_ns = $sig_attrs->getNamedItem(WSF_TYPE_NAMESPACE)->value;
                        }
                        //go to the next header
                        if ($header_first_child) {
                            $header_child = $header_first_child;
                            while ($header_child && ($header_child->nodeType == XML_TEXT_NODE || !($header_child->localName == $ele_name && $header_child->namespaceURI == $ele_ns))) {
                                $header_child = $header_child->nextSibling;
                            }
                        }
                        if ($header_child) {
                            $header_sig = $binding_details_child->firstChild;
                            if ($classmap != NULL && !empty($classmap)) {
                                ws_log_write(__FILE__, __LINE__, WSF_LOG_DEBUG, "starting to parse header {$ele_name} as a classmap");
                                $new_param = wsf_parse_payload_for_class_map($header_child, $header_sig, $ele_name, $classmap, $cid2cont_type, $cid2attachments);
                            } else {
                                ws_log_write(__FILE__, __LINE__, WSF_LOG_DEBUG, "starting to parse header {$ele_name} as an array");
                                $new_param = wsf_parse_payload_for_array($header_child, $header_sig, $cid2cont_type, $cid2attachments);
                            }
                            $header_params[] = $new_param;
                        }
                    }
                }
            }
        }
    }
    return array(WSF_RESPONSE_PAYLOAD_PARAM => $op_param_values, WSF_RESPONSE_HEADER_PARAM => $header_params);
}