This commit is contained in:
Andreas Schamberger 2011-10-02 12:23:59 +02:00
parent 06ff1ab707
commit 3040718c9d
3 changed files with 160 additions and 228 deletions

View File

@ -58,8 +58,7 @@ class Curl
public function __construct(array $options, $followLocationMaxRedirects = 10) public function __construct(array $options, $followLocationMaxRedirects = 10)
{ {
// set the default HTTP user agent // set the default HTTP user agent
if ( !isset( $options['user_agent'] ) ) if (!isset($options['user_agent'])) {
{
$options['user_agent'] = self::USER_AGENT; $options['user_agent'] = self::USER_AGENT;
} }
$this->followLocationMaxRedirects = $followLocationMaxRedirects; $this->followLocationMaxRedirects = $followLocationMaxRedirects;
@ -77,30 +76,24 @@ class Curl
CURLINFO_HEADER_OUT => true, CURLINFO_HEADER_OUT => true,
); );
curl_setopt_array($this->ch, $curlOptions); curl_setopt_array($this->ch, $curlOptions);
if ( isset( $options['compression'] ) && !( $options['compression'] & SOAP_COMPRESSION_ACCEPT ) ) if (isset($options['compression']) && !($options['compression'] & SOAP_COMPRESSION_ACCEPT)) {
{
curl_setopt($this->ch, CURLOPT_ENCODING, 'identity'); curl_setopt($this->ch, CURLOPT_ENCODING, 'identity');
} }
if ( isset( $options['connection_timeout'] ) ) if (isset($options['connection_timeout'])) {
{
curl_setopt($this->ch, CURLOPT_CONNECTTIMEOUT, $options['connection_timeout']); curl_setopt($this->ch, CURLOPT_CONNECTTIMEOUT, $options['connection_timeout']);
} }
if ( isset( $options['proxy_host'] ) ) if (isset($options['proxy_host'])) {
{
$port = isset($options['proxy_port']) ? $options['proxy_port'] : 8080; $port = isset($options['proxy_port']) ? $options['proxy_port'] : 8080;
curl_setopt($this->ch, CURLOPT_PROXY, $options['proxy_host'] . ':' . $port); curl_setopt($this->ch, CURLOPT_PROXY, $options['proxy_host'] . ':' . $port);
} }
if ( isset( $options['proxy_user'] ) ) if (isset($options['proxy_user'])) {
{
curl_setopt($this->ch, CURLOPT_PROXYUSERPWD, $options['proxy_user'] . ':' . $options['proxy_password']); curl_setopt($this->ch, CURLOPT_PROXYUSERPWD, $options['proxy_user'] . ':' . $options['proxy_password']);
} }
if ( isset( $options['login'] ) ) if (isset($options['login'])) {
{
curl_setopt($this->ch, CURLOPT_HTTPAUTH, CURLAUTH_ANY); curl_setopt($this->ch, CURLOPT_HTTPAUTH, CURLAUTH_ANY);
curl_setopt($this->ch, CURLOPT_USERPWD, $options['login'].':'.$options['password']); curl_setopt($this->ch, CURLOPT_USERPWD, $options['login'].':'.$options['password']);
} }
if ( isset( $options['local_cert'] ) ) if (isset($options['local_cert'])) {
{
curl_setopt($this->ch, CURLOPT_SSLCERT, $options['local_cert']); curl_setopt($this->ch, CURLOPT_SSLCERT, $options['local_cert']);
curl_setopt($this->ch, CURLOPT_SSLCERTPASSWD, $options['passphrase']); curl_setopt($this->ch, CURLOPT_SSLCERTPASSWD, $options['passphrase']);
} }
@ -127,14 +120,12 @@ class Curl
{ {
curl_setopt($this->ch, CURLOPT_URL, $location); curl_setopt($this->ch, CURLOPT_URL, $location);
if ( !is_null( $request ) ) if (!is_null($request)) {
{
curl_setopt($this->ch, CURLOPT_POST, true); curl_setopt($this->ch, CURLOPT_POST, true);
curl_setopt($this->ch, CURLOPT_POSTFIELDS, $request); curl_setopt($this->ch, CURLOPT_POSTFIELDS, $request);
} }
if ( count( $requestHeaders ) > 0 ) if (count($requestHeaders) > 0) {
{
curl_setopt($this->ch, CURLOPT_HTTPHEADER, $requestHeaders); curl_setopt($this->ch, CURLOPT_HTTPHEADER, $requestHeaders);
} }
@ -154,8 +145,7 @@ class Curl
*/ */
private function execManualRedirect($redirects = 0) private function execManualRedirect($redirects = 0)
{ {
if ( $redirects > $this->followLocationMaxRedirects ) if ($redirects > $this->followLocationMaxRedirects) {
{
// TODO Redirection limit reached, aborting // TODO Redirection limit reached, aborting
return false; return false;
} }
@ -163,27 +153,22 @@ class Curl
curl_setopt($this->ch, CURLOPT_RETURNTRANSFER, true); curl_setopt($this->ch, CURLOPT_RETURNTRANSFER, true);
$response = curl_exec($this->ch); $response = curl_exec($this->ch);
$httpResponseCode = curl_getinfo($this->ch, CURLINFO_HTTP_CODE); $httpResponseCode = curl_getinfo($this->ch, CURLINFO_HTTP_CODE);
if ( $httpResponseCode == 307 ) if ($httpResponseCode == 307) {
{
$headerSize = curl_getinfo($this->ch, CURLINFO_HEADER_SIZE); $headerSize = curl_getinfo($this->ch, CURLINFO_HEADER_SIZE);
$header = substr($response, 0, $headerSize); $header = substr($response, 0, $headerSize);
$matches = array(); $matches = array();
preg_match('/Location:(.*?)\n/', $header, $matches); preg_match('/Location:(.*?)\n/', $header, $matches);
$url = trim(array_pop($matches)); $url = trim(array_pop($matches));
// @parse_url to suppress E_WARNING for invalid urls // @parse_url to suppress E_WARNING for invalid urls
if ( ( $url = @parse_url( $url ) ) !== false ) if (($url = @parse_url($url)) !== false) {
{
$lastUrl = parse_url(curl_getinfo($this->ch, CURLINFO_EFFECTIVE_URL)); $lastUrl = parse_url(curl_getinfo($this->ch, CURLINFO_EFFECTIVE_URL));
if ( !isset( $url['scheme'] ) ) if (!isset($url['scheme'])) {
{
$url['scheme'] = $lastUrl['scheme']; $url['scheme'] = $lastUrl['scheme'];
} }
if ( !isset( $url['host'] ) ) if (!isset($url['host'])) {
{
$url['host'] = $lastUrl['host']; $url['host'] = $lastUrl['host'];
} }
if ( !isset( $url['path'] ) ) if (!isset($url['path'])) {
{
$url['path'] = $lastUrl['path']; $url['path'] = $lastUrl['path'];
} }
$newUrl = $url['scheme'] . '://' . $url['host'] . $url['path'] . ($url['query'] ? '?' . $url['query'] : ''); $newUrl = $url['scheme'] . '://' . $url['host'] . $url['path'] . ($url['query'] ? '?' . $url['query'] : '');
@ -241,8 +226,7 @@ class Curl
{ {
$errorCodeMapping = $this->getErrorCodeMapping(); $errorCodeMapping = $this->getErrorCodeMapping();
$errorNumber = curl_errno($this->ch); $errorNumber = curl_errno($this->ch);
if ( isset( $errorCodeMapping[$errorNumber] ) ) if (isset($errorCodeMapping[$errorNumber])) {
{
return $errorCodeMapping[$errorNumber]; return $errorCodeMapping[$errorNumber];
} }
return curl_error($this->ch); return curl_error($this->ch);

View File

@ -174,8 +174,7 @@ class Helper
public static function exceptionErrorHandler($errno, $errstr, $errfile, $errline) public static function exceptionErrorHandler($errno, $errstr, $errfile, $errline)
{ {
// don't throw exception for errors suppresed with @ // don't throw exception for errors suppresed with @
if ( error_reporting() != 0 ) if (error_reporting() != 0) {
{
throw new \ErrorException($errstr, 0, $errno, $errfile, $errline); throw new \ErrorException($errstr, 0, $errno, $errfile, $errline);
} }
} }
@ -215,17 +214,13 @@ class Helper
{ {
$url = ''; $url = '';
if (isset($_SERVER['HTTPS']) && if (isset($_SERVER['HTTPS']) &&
( strtolower( $_SERVER['HTTPS'] ) === 'on' || $_SERVER['HTTPS'] === '1' ) ) (strtolower($_SERVER['HTTPS']) === 'on' || $_SERVER['HTTPS'] === '1')) {
{
$url .= 'https://'; $url .= 'https://';
} } else {
else
{
$url .= 'http://'; $url .= 'http://';
} }
$url .= isset($_SERVER['SERVER_NAME']) ? $_SERVER['SERVER_NAME'] : ''; $url .= isset($_SERVER['SERVER_NAME']) ? $_SERVER['SERVER_NAME'] : '';
if ( isset( $_SERVER['SERVER_PORT'] ) && $_SERVER['SERVER_PORT'] != 80 ) if (isset($_SERVER['SERVER_PORT']) && $_SERVER['SERVER_PORT'] != 80) {
{
$url .= ":{$_SERVER['SERVER_PORT']}"; $url .= ":{$_SERVER['SERVER_PORT']}";
} }
$url .= isset($_SERVER['REQUEST_URI']) ? $_SERVER['REQUEST_URI'] : ''; $url .= isset($_SERVER['REQUEST_URI']) ? $_SERVER['REQUEST_URI'] : '';
@ -240,12 +235,9 @@ class Helper
*/ */
public static function getSoapNamespace($version) public static function getSoapNamespace($version)
{ {
if ( $version === SOAP_1_2 ) if ($version === SOAP_1_2) {
{
return self::NS_SOAP_1_2; return self::NS_SOAP_1_2;
} } else {
else
{
return self::NS_SOAP_1_1; return self::NS_SOAP_1_1;
} }
} }
@ -258,12 +250,9 @@ class Helper
*/ */
public static function getSoapVersionFromNamespace($namespace) public static function getSoapVersionFromNamespace($namespace)
{ {
if ( $namespace === self::NS_SOAP_1_2 ) if ($namespace === self::NS_SOAP_1_2) {
{
return SOAP_1_2; return SOAP_1_2;
} } else {
else
{
return SOAP_1_1; return SOAP_1_1;
} }
} }
@ -281,8 +270,7 @@ class Helper
*/ */
public static function runPlugins(array $plugins, $requestType, $xml, $location = null, $action = null, \ass\Soap\WsdlHandler $wsdlHandler = null) public static function runPlugins(array $plugins, $requestType, $xml, $location = null, $action = null, \ass\Soap\WsdlHandler $wsdlHandler = null)
{ {
if ( count( $plugins ) > 0 ) if (count($plugins) > 0) {
{
// instantiate new dom object // instantiate new dom object
$dom = new \DOMDocument('1.0'); $dom = new \DOMDocument('1.0');
// format the XML if option is set // format the XML if option is set
@ -294,28 +282,21 @@ class Helper
$action, $action,
$wsdlHandler $wsdlHandler
); );
if ( $requestType == self::REQUEST ) if ($requestType == self::REQUEST) {
{
$callMethod = 'modifyRequest'; $callMethod = 'modifyRequest';
} } else {
else
{
$callMethod = 'modifyResponse'; $callMethod = 'modifyResponse';
} }
// modify dom // modify dom
foreach( $plugins AS $plugin ) foreach($plugins AS $plugin) {
{ if ($plugin instanceof \ass\Soap\Plugin) {
if ( $plugin instanceof \ass\Soap\Plugin )
{
call_user_func_array(array($plugin, $callMethod), $params); call_user_func_array(array($plugin, $callMethod), $params);
} }
} }
// return the modified xml document // return the modified xml document
return $dom->saveXML(); return $dom->saveXML();
}
// format the XML if option is set // format the XML if option is set
elseif ( self::$formatXmlOutput === true ) } elseif (self::$formatXmlOutput === true) {
{
$dom = new \DOMDocument('1.0'); $dom = new \DOMDocument('1.0');
$dom->formatOutput = true; $dom->formatOutput = true;
$dom->loadXML($xml); $dom->loadXML($xml);
@ -331,13 +312,10 @@ class Helper
*/ */
public static function setCustomErrorHandler($reset = false) public static function setCustomErrorHandler($reset = false)
{ {
if ( $reset === true && !is_null( self::$previousErrorHandler ) ) if ($reset === true && !is_null(self::$previousErrorHandler)) {
{
set_error_handler(self::$previousErrorHandler); set_error_handler(self::$previousErrorHandler);
self::$previousErrorHandler = null; self::$previousErrorHandler = null;
} } else {
else
{
self::$previousErrorHandler = set_error_handler('ass\\Soap\\Helper::exceptionErrorHandler'); self::$previousErrorHandler = set_error_handler('ass\\Soap\\Helper::exceptionErrorHandler');
} }
return self::$previousErrorHandler; return self::$previousErrorHandler;
@ -384,12 +362,9 @@ class Helper
*/ */
public static function setHttpStatusHeader($header) public static function setHttpStatusHeader($header)
{ {
if ( substr( php_sapi_name(), 0, 3 ) == 'cgi' ) if ('cgi' == substr(php_sapi_name(), 0, 3)) {
{
header('Status: ' . $header); header('Status: ' . $header);
} } else {
else
{
header($_SERVER['SERVER_PROTOCOL'] . ' ' . $header); header($_SERVER['SERVER_PROTOCOL'] . ' ' . $header);
} }
} }

View File

@ -80,30 +80,23 @@ class SoapClient extends \SoapClient
// set custom error handler that converts all php errors to ErrorExceptions // set custom error handler that converts all php errors to ErrorExceptions
Helper::setCustomErrorHandler(); Helper::setCustomErrorHandler();
// we want to make sure we have the soap version to rely on it later // we want to make sure we have the soap version to rely on it later
if ( !isset( $options['soap_version'] ) ) if (!isset($options['soap_version'])) {
{
$options['soap_version'] = SOAP_1_1; $options['soap_version'] = SOAP_1_1;
} }
// we want to make sure we have the features option // we want to make sure we have the features option
if ( !isset( $options['features'] ) ) if (!isset($options['features'])) {
{
$options['features'] = 0; $options['features'] = 0;
} }
// set default option to resolve xsd includes // set default option to resolve xsd includes
if ( !isset( $options['resolve_xsd_includes'] ) ) if (!isset($options['resolve_xsd_includes'])) {
{
$options['resolve_xsd_includes'] = true; $options['resolve_xsd_includes'] = true;
} }
// add type converters from TypeConverterCollection // add type converters from TypeConverterCollection
if ( !is_null( $converters ) ) if (!is_null($converters)) {
{
$convertersTypemap = $converters->getTypemap(); $convertersTypemap = $converters->getTypemap();
if ( isset( $options['typemap'] ) ) if (isset($options['typemap'])) {
{
$options['typemap'] = array_merge($options['typemap'], $convertersTypemap); $options['typemap'] = array_merge($options['typemap'], $convertersTypemap);
} } else {
else
{
$options['typemap'] = $convertersTypemap; $options['typemap'] = $convertersTypemap;
} }
} }
@ -131,14 +124,11 @@ class SoapClient extends \SoapClient
{ {
// $request is if unmodified from SoapClient not a php string type! // $request is if unmodified from SoapClient not a php string type!
$request = (string)$request; $request = (string)$request;
if ( $this->options['soap_version'] == SOAP_1_2 ) if ($this->options['soap_version'] == SOAP_1_2) {
{
$headers = array( $headers = array(
'Content-Type: application/soap+xml; charset=utf-8', 'Content-Type: application/soap+xml; charset=utf-8',
); );
} } else {
else
{
$headers = array( $headers = array(
'Content-Type: text/xml; charset=utf-8', 'Content-Type: text/xml; charset=utf-8',
); );
@ -150,14 +140,12 @@ class SoapClient extends \SoapClient
// execute request // execute request
$responseSuccessfull = $curl->exec($location, $request, $headers); $responseSuccessfull = $curl->exec($location, $request, $headers);
// tracing enabled: store last request header and body // tracing enabled: store last request header and body
if ( isset( $this->options['trace'] ) && $this->options['trace'] === true ) if (isset($this->options['trace']) && $this->options['trace'] === true) {
{
$this->lastRequestHeaders = $curl->getRequestHeaders(); $this->lastRequestHeaders = $curl->getRequestHeaders();
$this->lastRequest = $request; $this->lastRequest = $request;
} }
// in case of an error while making the http request throw a soapFault // in case of an error while making the http request throw a soapFault
if ( $responseSuccessfull === false ) if ($responseSuccessfull === false) {
{
// get error message from curl // get error message from curl
$faultstring = $curl->getErrorMessage(); $faultstring = $curl->getErrorMessage();
// destruct curl object // destruct curl object
@ -165,8 +153,7 @@ class SoapClient extends \SoapClient
throw new \SoapFault('HTTP', $faultstring); throw new \SoapFault('HTTP', $faultstring);
} }
// tracing enabled: store last response header and body // tracing enabled: store last response header and body
if ( isset( $this->options['trace'] ) && $this->options['trace'] === true ) if (isset($this->options['trace']) && $this->options['trace'] === true) {
{
$this->lastResponseHeaders = $curl->getResponseHeaders(); $this->lastResponseHeaders = $curl->getResponseHeaders();
$this->lastResponse = $curl->getResponseBody(); $this->lastResponse = $curl->getResponseBody();
} }
@ -174,38 +161,27 @@ class SoapClient extends \SoapClient
// check if we do have a proper soap status code (if not soapfault) // check if we do have a proper soap status code (if not soapfault)
// // TODO // // TODO
// $responseStatusCode = $curl->getResponseStatusCode(); // $responseStatusCode = $curl->getResponseStatusCode();
// if ( $responseStatusCode >= 400 ) // if ($responseStatusCode >= 400) {
// {
// $isError = 0; // $isError = 0;
// $response = trim($response); // $response = trim($response);
// if ( strlen( $response ) == 0 ) // if (strlen($response) == 0) {
// {
// $isError = 1; // $isError = 1;
// } // } else {
// else
// {
// $contentType = $curl->getResponseContentType(); // $contentType = $curl->getResponseContentType();
// if ($contentType != 'application/soap+xml' // if ($contentType != 'application/soap+xml'
// && $contentType != 'application/soap+xml' ) // && $contentType != 'application/soap+xml') {
// { // if (strncmp($response , "<?xml", 5)) {
// if ( strncmp( $response , "<?xml", 5 ) )
// {
// $isError = 1; // $isError = 1;
// } // }
// } // }
// } // }
// if ( $isError == 1 ) // if ($isError == 1) {
// {
// throw new \SoapFault('HTTP', $curl->getResponseStatusMessage()); // throw new \SoapFault('HTTP', $curl->getResponseStatusMessage());
// } // }
// } // } elseif ($responseStatusCode != 200 && $responseStatusCode != 202) {
// // TODO
// elseif ( $responseStatusCode != 200 && $responseStatusCode != 202 )
// {
// $dom = new \DOMDocument('1.0'); // $dom = new \DOMDocument('1.0');
// $dom->loadXML($response); // $dom->loadXML($response);
// if ( $dom->getElementsByTagNameNS( $dom->documentElement->namespaceURI, 'Fault' )->length == 0 ) // if ($dom->getElementsByTagNameNS($dom->documentElement->namespaceURI, 'Fault')->length == 0) {
// {
// throw new \SoapFault('HTTP', 'HTTP response status must be 200 or 202'); // throw new \SoapFault('HTTP', 'HTTP response status must be 200 or 202');
// } // }
// } // }
@ -284,12 +260,9 @@ class SoapClient extends \SoapClient
private function loadWsdl($wsdl) private function loadWsdl($wsdl)
{ {
$wsdlDownloader = new WsdlDownloader($this->options); $wsdlDownloader = new WsdlDownloader($this->options);
try try {
{
$cacheFileName = $wsdlDownloader->download($wsdl); $cacheFileName = $wsdlDownloader->download($wsdl);
} } catch (\RuntimeException $e) {
catch ( \RuntimeException $e )
{
throw new \SoapFault('WSDL', "SOAP-ERROR: Parsing WSDL: Couldn't load from '" . $wsdl . "' : failed to load external entity \"" . $wsdl . "\""); throw new \SoapFault('WSDL', "SOAP-ERROR: Parsing WSDL: Couldn't load from '" . $wsdl . "' : failed to load external entity \"" . $wsdl . "\"");
} }
return $cacheFileName; return $cacheFileName;