/** * constructor * * @param string $faultcode (SOAP-ENV:Client | SOAP-ENV:Server) * @param string $faultactor only used when msg routed between multiple actors * @param string $faultstring human readable error message * @param mixed $faultdetail detail, typically a string or array of string */ function soap_fault($faultcode, $faultactor = '', $faultstring = '', $faultdetail = '') { parent::soap_base(); $this->faultcode = $faultcode; $this->faultactor = $faultactor; $this->faultstring = $faultstring; $this->faultdetail = $faultdetail; }
/** * constructor */ function soap_transport_http($url) { parent::soap_base(); $this->setURL($url); ereg('\\$Revisio' . 'n: ([^ ]+)', $this->revision, $rev); $this->outgoing_headers['User-Agent'] = $this->title . '/' . $this->version . ' (' . $rev[1] . ')'; $this->debug('set User-Agent: ' . $this->outgoing_headers['User-Agent']); }
/** * constructor * * @param string $schema schema document URI * @param string $xml xml document URI * @param string $namespaces namespaces defined in enclosing XML * @access public */ function XMLSchema($schema = '', $xml = '', $namespaces = array()) { parent::soap_base(); $this->debug('xmlschema class instantiated, inside constructor'); // files $this->schema = $schema; $this->xml = $xml; // namespaces $this->enclosingNamespaces = $namespaces; $this->namespaces = array_merge($this->namespaces, $namespaces); // parse schema file if ($schema != '') { $this->debug('initial schema file: ' . $schema); $this->parseFile($schema, 'schema'); } // parse xml file if ($xml != '') { $this->debug('initial xml file: ' . $xml); $this->parseFile($xml, 'xml'); } }
/** * constructor * * @param string $wsdl WSDL document URL * @param string $proxyhost * @param string $proxyport * @param string $proxyusername * @param string $proxypassword * @param integer $timeout set the connection timeout * @param integer $response_timeout set the response timeout * @access public */ function wsdl($wsdl = '', $proxyhost = false, $proxyport = false, $proxyusername = false, $proxypassword = false, $timeout = 0, $response_timeout = 30) { parent::soap_base(); $this->wsdl = $wsdl; $this->proxyhost = $proxyhost; $this->proxyport = $proxyport; $this->proxyusername = $proxyusername; $this->proxypassword = $proxypassword; $this->timeout = $timeout; $this->response_timeout = $response_timeout; // parse wsdl file if ($wsdl != "") { $this->debug('initial wsdl URL: ' . $wsdl); $this->parseWSDL($wsdl); } // imports // TODO: handle imports more properly, grabbing them in-line and nesting them $imported_urls = array(); $imported = 1; while ($imported > 0) { $imported = 0; // Schema imports foreach ($this->schemas as $ns => $list) { foreach ($list as $xs) { $wsdlparts = parse_url($this->wsdl); // this is bogusly simple! foreach ($xs->imports as $ns2 => $list2) { for ($ii = 0; $ii < count($list2); $ii++) { if (!$list2[$ii]['loaded']) { $this->schemas[$ns]->imports[$ns2][$ii]['loaded'] = true; $url = $list2[$ii]['location']; if ($url != '') { $urlparts = parse_url($url); if (!isset($urlparts['host'])) { $url = $wsdlparts['scheme'] . '://' . $wsdlparts['host'] . (isset($wsdlparts['port']) ? ':' . $wsdlparts['port'] : '') . substr($wsdlparts['path'], 0, strrpos($wsdlparts['path'], '/') + 1) . $urlparts['path']; } if (!in_array($url, $imported_urls)) { $this->parseWSDL($url); $imported++; $imported_urls[] = $url; } } else { $this->debug("Unexpected scenario: empty URL for unloaded import"); } } } } } } // WSDL imports $wsdlparts = parse_url($this->wsdl); // this is bogusly simple! foreach ($this->import as $ns => $list) { for ($ii = 0; $ii < count($list); $ii++) { if (!$list[$ii]['loaded']) { $this->import[$ns][$ii]['loaded'] = true; $url = $list[$ii]['location']; if ($url != '') { $urlparts = parse_url($url); if (!isset($urlparts['host'])) { $url = $wsdlparts['scheme'] . '://' . $wsdlparts['host'] . (isset($wsdlparts['port']) ? ':' . $wsdlparts['port'] : '') . substr($wsdlparts['path'], 0, strrpos($wsdlparts['path'], '/') + 1) . $urlparts['path']; } if (!in_array($url, $imported_urls)) { $this->parseWSDL($url); $imported++; $imported_urls[] = $url; } } else { $this->debug("Unexpected scenario: empty URL for unloaded import"); } } } } } // add new data to operation data foreach ($this->bindings as $binding => $bindingData) { if (isset($bindingData['operations']) && is_array($bindingData['operations'])) { foreach ($bindingData['operations'] as $operation => $data) { $this->debug('post-parse data gathering for ' . $operation); $this->bindings[$binding]['operations'][$operation]['input'] = isset($this->bindings[$binding]['operations'][$operation]['input']) ? array_merge($this->bindings[$binding]['operations'][$operation]['input'], $this->portTypes[$bindingData['portType']][$operation]['input']) : $this->portTypes[$bindingData['portType']][$operation]['input']; $this->bindings[$binding]['operations'][$operation]['output'] = isset($this->bindings[$binding]['operations'][$operation]['output']) ? array_merge($this->bindings[$binding]['operations'][$operation]['output'], $this->portTypes[$bindingData['portType']][$operation]['output']) : $this->portTypes[$bindingData['portType']][$operation]['output']; if (isset($this->messages[$this->bindings[$binding]['operations'][$operation]['input']['message']])) { $this->bindings[$binding]['operations'][$operation]['input']['parts'] = $this->messages[$this->bindings[$binding]['operations'][$operation]['input']['message']]; } if (isset($this->messages[$this->bindings[$binding]['operations'][$operation]['output']['message']])) { $this->bindings[$binding]['operations'][$operation]['output']['parts'] = $this->messages[$this->bindings[$binding]['operations'][$operation]['output']['message']]; } if (isset($bindingData['style'])) { $this->bindings[$binding]['operations'][$operation]['style'] = $bindingData['style']; } $this->bindings[$binding]['operations'][$operation]['transport'] = isset($bindingData['transport']) ? $bindingData['transport'] : ''; $this->bindings[$binding]['operations'][$operation]['documentation'] = isset($this->portTypes[$bindingData['portType']][$operation]['documentation']) ? $this->portTypes[$bindingData['portType']][$operation]['documentation'] : ''; $this->bindings[$binding]['operations'][$operation]['endpoint'] = isset($bindingData['endpoint']) ? $bindingData['endpoint'] : ''; } } } }
/** * constructor * the optional parameter is a path to a WSDL file that you'd like to bind the server instance to. * * @param mixed $wsdl file path or URL (string), or wsdl instance (object) * @access public */ function soap_server($wsdl = false) { parent::soap_base(); // turn on debugging? global $debug; global $HTTP_SERVER_VARS; if (isset($_SERVER)) { $this->debug("_SERVER is defined:"); $this->appendDebug($this->varDump($_SERVER)); } elseif (isset($HTTP_SERVER_VARS)) { $this->debug("HTTP_SERVER_VARS is defined:"); $this->appendDebug($this->varDump($HTTP_SERVER_VARS)); } else { $this->debug("Neither _SERVER nor HTTP_SERVER_VARS is defined."); } if (isset($debug)) { $this->debug("In soap_server, set debug_flag={$debug} based on global flag"); $this->debug_flag = $debug; } elseif (isset($_SERVER['QUERY_STRING'])) { $qs = explode('&', $_SERVER['QUERY_STRING']); foreach ($qs as $v) { if (substr($v, 0, 6) == 'debug=') { $this->debug("In soap_server, set debug_flag=" . substr($v, 6) . " based on query string #1"); $this->debug_flag = substr($v, 6); } } } elseif (isset($HTTP_SERVER_VARS['QUERY_STRING'])) { $qs = explode('&', $HTTP_SERVER_VARS['QUERY_STRING']); foreach ($qs as $v) { if (substr($v, 0, 6) == 'debug=') { $this->debug("In soap_server, set debug_flag=" . substr($v, 6) . " based on query string #2"); $this->debug_flag = substr($v, 6); } } } // wsdl if ($wsdl) { $this->debug("In soap_server, WSDL is specified"); if (is_object($wsdl) && get_class($wsdl) == 'wsdl') { $this->wsdl = $wsdl; $this->externalWSDLURL = $this->wsdl->wsdl; $this->debug('Use existing wsdl instance from ' . $this->externalWSDLURL); } else { $this->debug('Create wsdl from ' . $wsdl); $this->wsdl = new wsdl($wsdl); $this->externalWSDLURL = $wsdl; } $this->appendDebug($this->wsdl->getDebug()); $this->wsdl->clearDebug(); if ($err = $this->wsdl->getError()) { die('WSDL ERROR: ' . $err); } } }
/** * constructor that actually does the parsing * * @param string $xml SOAP message * @param string $encoding character encoding scheme of message * @param string $method method for which XML is parsed (unused?) * @param string $decode_utf8 whether to decode UTF-8 to ISO-8859-1 * @access public */ function soap_parser($xml, $encoding = 'UTF-8', $method = '', $decode_utf8 = true) { parent::soap_base(); $this->xml = $xml; $this->xml_encoding = $encoding; $this->method = $method; $this->decode_utf8 = $decode_utf8; // Check whether content has been read. if (!empty($xml)) { // Check XML encoding $pos_xml = strpos($xml, '<?xml'); if ($pos_xml !== FALSE) { $xml_decl = substr($xml, $pos_xml, strpos($xml, '?>', $pos_xml + 2) - $pos_xml + 1); if (preg_match("/encoding=[\"']([^\"']*)[\"']/", $xml_decl, $res)) { $xml_encoding = $res[1]; if (strtoupper($xml_encoding) != $encoding) { $err = "Charset from HTTP Content-Type '" . $encoding . "' does not match encoding from XML declaration '" . $xml_encoding . "'"; $this->debug($err); if ($encoding != 'ISO-8859-1' || strtoupper($xml_encoding) != 'UTF-8') { $this->setError($err); return; } // when HTTP says ISO-8859-1 (the default) and XML says UTF-8 (the typical), assume the other endpoint is just sloppy and proceed } else { $this->debug('Charset from HTTP Content-Type matches encoding from XML declaration'); } } else { $this->debug('No encoding specified in XML declaration'); } } else { $this->debug('No XML declaration'); } $this->debug('Entering soap_parser(), length=' . strlen($xml) . ', encoding=' . $encoding); // Create an XML parser - why not xml_parser_create_ns? $this->parser = xml_parser_create($this->xml_encoding); // Set the options for parsing the XML data. //xml_parser_set_option($parser, XML_OPTION_SKIP_WHITE, 1); xml_parser_set_option($this->parser, XML_OPTION_CASE_FOLDING, 0); xml_parser_set_option($this->parser, XML_OPTION_TARGET_ENCODING, $this->xml_encoding); // Set the object for the parser. xml_set_object($this->parser, $this); // Set the element handlers for the parser. xml_set_element_handler($this->parser, 'start_element', 'end_element'); xml_set_character_data_handler($this->parser, 'character_data'); // Parse the XML file. if (!xml_parse($this->parser, $xml, true)) { // Display an error message. $err = sprintf('XML error parsing SOAP payload on line %d: %s', xml_get_current_line_number($this->parser), xml_error_string(xml_get_error_code($this->parser))); $this->debug($err); $this->debug("XML payload:\n" . $xml); $this->setError($err); } else { $this->debug('parsed successfully, found root struct: ' . $this->root_struct . ' of name ' . $this->root_struct_name); // get final value $this->soapresponse = $this->message[$this->root_struct]['result']; // get header value: no, because this is documented as XML string // if($this->root_header != '' && isset($this->message[$this->root_header]['result'])){ // $this->responseHeaders = $this->message[$this->root_header]['result']; // } // resolve hrefs/ids if (sizeof($this->multirefs) > 0) { foreach ($this->multirefs as $id => $hrefs) { $this->debug('resolving multirefs for id: ' . $id); $idVal = $this->buildVal($this->ids[$id]); if (is_array($idVal) && isset($idVal['!id'])) { unset($idVal['!id']); } foreach ($hrefs as $refPos => $ref) { $this->debug('resolving href at pos ' . $refPos); $this->multirefs[$id][$refPos] = $idVal; } } } } xml_parser_free($this->parser); } else { $this->debug('xml was empty, didn\'t parse!'); $this->setError('xml was empty, didn\'t parse!'); } }
/** * constructor * * @param string $name optional name * @param mixed $type optional type name * @param mixed $value optional value * @param mixed $element_ns optional namespace of value * @param mixed $type_ns optional namespace of type * @param mixed $attributes associative array of attributes to add to element serialization * @access public */ function soap_val($name = 'soapval', $type = false, $value = -1, $element_ns = false, $type_ns = false, $attributes = false) { parent::soap_base(); $this->name = $name; $this->type = $type; $this->value = $value; $this->element_ns = $element_ns; $this->type_ns = $type_ns; $this->attributes = $attributes; }
/** * constructor * * @param mixed $endpoint SOAP server or WSDL URL (string), or wsdl instance (object) * @param bool $wsdl optional, set to true if using WSDL * @param int $portName optional portName in WSDL document * @param string $proxyhost * @param string $proxyport * @param string $proxyusername * @param string $proxypassword * @param integer $timeout set the connection timeout * @param integer $response_timeout set the response timeout * @access public */ function soap_client($endpoint, $wsdl = false, $proxyhost = false, $proxyport = false, $proxyusername = false, $proxypassword = false, $timeout = 0, $response_timeout = 30) { parent::soap_base(); $this->endpoint = $endpoint; $this->proxyhost = $proxyhost; $this->proxyport = $proxyport; $this->proxyusername = $proxyusername; $this->proxypassword = $proxypassword; $this->timeout = $timeout; $this->response_timeout = $response_timeout; // make values if ($wsdl) { if (is_object($endpoint) && get_class($endpoint) == 'wsdl') { $this->wsdl = $endpoint; $this->endpoint = $this->wsdl->wsdl; $this->wsdlFile = $this->endpoint; $this->debug('existing wsdl instance created from ' . $this->endpoint); } else { $this->wsdlFile = $this->endpoint; // instantiate wsdl object and parse wsdl file $this->debug('instantiating wsdl class with doc: ' . $endpoint); $this->wsdl =& new wsdl($this->wsdlFile, $this->proxyhost, $this->proxyport, $this->proxyusername, $this->proxypassword, $this->timeout, $this->response_timeout); } $this->appendDebug($this->wsdl->getDebug()); $this->wsdl->clearDebug(); // catch errors if ($errstr = $this->wsdl->getError()) { $this->debug('got wsdl error: ' . $errstr); $this->setError('wsdl error: ' . $errstr); } elseif ($this->operations = $this->wsdl->getOperations()) { $this->debug('got ' . count($this->operations) . ' operations from wsdl ' . $this->wsdlFile); $this->endpointType = 'wsdl'; } else { $this->debug('getOperations returned false'); $this->setError('no operations defined in the WSDL document!'); } } else { $this->debug("instantiate SOAP with endpoint at {$endpoint}"); $this->endpointType = 'soap'; } }