PHP soap 大数据同步问题

hedongli 2011-07-10

问题描述:

假如你的php soap客户端不能正常的同步数据,但你直接调用服务端相应的方法又是正常的,那有可能是default_socket_timeout值过小引起的(可在php.ini文件中设置),默认情况下它的值为60 ,表示socket的过期时间为60s,如果你要作大量的数据同步,尤其是需要轮循的取出数据,那应把该值设置大一些,具体视同步时间长短而定。

如下是php手册对soap的示例,最下方的描述谈到过关于default_socket_timeout值的设置问题。

The SoapClient class

简介

The SoapClient class provides a client for ? SOAP 1.1, ? SOAP 1.2 servers. It can be used in WSDL or non-WSDL mode.

类摘要

SoapClient {

public mixed __call ( string $function_name , string $arguments )
SoapClient ( mixed $wsdl [, array $options ] )
public string __doRequest ( string $request , string $location , string $action , int $version [, int $one_way = 0 ] )
public array __getFunctions ( void )
public string __getLastRequest ( void )
public string __getLastRequestHeaders ( void )
public string __getLastResponse ( void )
public string __getLastResponseHeaders ( void )
public array __getTypes ( void )
public void __setCookie ( string $name [, string $value ] )
public string __setLocation ([ string $new_location ] )
public bool __setSoapHeaders ([ mixed $soapheaders ] )
public mixed __soapCall ( string $function_name , array $arguments [, array $options [, mixed $input_headers [, array &$output_headers ]]] )
SoapClient ( mixed $wsdl [, array $options ] )
}
Table of Contents

SoapClient::__call — Calls a SOAP function (deprecated)
SoapClient::__construct — SoapClient constructor
SoapClient::__doRequest — Performs a SOAP request
SoapClient::__getFunctions — Returns list of available SOAP functions
SoapClient::__getLastRequest — Returns last SOAP request
SoapClient::__getLastRequestHeaders — Returns the SOAP headers from the last request
SoapClient::__getLastResponse — Returns last SOAP response
SoapClient::__getLastResponseHeaders — Returns the SOAP headers from the last response
SoapClient::__getTypes — Returns a list of SOAP types
SoapClient::__setCookie — The __setCookie purpose
SoapClient::__setLocation — Sets the location of the Web service to use
SoapClient::__setSoapHeaders — Sets SOAP headers for subsequent calls
SoapClient::__soapCall — Calls a SOAP function
SoapClient::SoapClient — SoapClient constructor

SoapClient::__call use_soap_error_handler
[edit] Last updated: Fri, 01 Jul 2011
   add a noteUser Contributed Notes SoapClient
stepan dot zarubin at gmail dot com 30-Jun-2011 06:51
Well, this example works fine:

<?php
try {
    $x = @new SoapClient("non-existent.wsdl");
} catch (Exception $e) {
    echo $e->getMessage();
}
?>

Just make sure use NEW with @.
tlk 19-May-2011 01:35
Make sure to prefix constructor calls with @ and catch SoapFault exceptions, otherwise you risk having the php interpreter exit/die on simple network issues.

Robust sample code by Rasmus from http://bugs.php.net/bug.php?id=47584

<?php
try {
    $x = @new SoapClient("non-existent.wsdl",array("exceptions" => 1));
} catch (SoapFault $E) {
    echo $E->faultstring;
}
echo "ok\n";
?>
jjlopez 09-Mar-2011 07:36
If you are making soap calls in WSDL mode , and the address of your web service includes a port different from 80 (like http://my_ip_address:8080//service.asmx?wsdl), the WSDL file is fetched correctly, but all subsequent requests are made without any port in the host field. This causes a SoapFault exception when trying to call any of the service’s methods.

You need to redefine the soapClient class and force the port in each call.

See this example:

http://www.victorstanciu.ro/php-soapclient-port-bug-workaround/
hugues at zonereseau dot com 18-Feb-2011 05:17
When you need to connect to services requiring to send extra header use this method.

Here how we can to it with PHP and SoapClient

<?php
class exampleChannelAdvisorAuth
{
    public $DeveloperKey;
    public $Password;

    public function __construct($key, $pass)
    {
        $this->DeveloperKey = $key;
        $this->Password = $pass;
    }
}

$devKey        = "";
$password    = "";
$accountId    = "";

// Create the SoapClient instance
$url         = "";
$client     = new SoapClient($url, array("trace" => 1, "exception" => 0));

// Create the header
$auth         = new ChannelAdvisorAuth($devKey, $password);
$header     = new SoapHeader("http://www.example.com/webservices/", "APICredentials", $auth, false);

// Call wsdl function
$result = $client->__soapCall("DeleteMarketplaceAd", array(
    "DeleteMarketplaceAd" => array(
        "accountID"        => $accountId,
        "marketplaceAdID"    => "9938745"        // The ads ID
    )
), NULL, $header);

// Echo the result
echo "<pre>".print_r($result, true)."</pre>";
if($result->DeleteMarketplaceAdResult->Status == "Success")
{
    echo "Item deleted!";
}
?>
jeffmixpute 24-Jan-2011 11:15
Simple php client and server:

Client:

<?php

// bind SOAP/Client.php -> path of the php file
require_once "SOAP/Client.php";

// URI delivered to web service
$sc = new SOAP_Client("http://localhost/SOAP/Server.php");

// start call function to use the function of the Web Service
$parameter = array();
$result = $sc->call ("now", &$parameter, "urn:TimeSerivce");

// print result
print $result."\n";

?>

Server:

<?php

// bind PEAR::SOAP
require_once "SOAP/Server.php";
$skiptrace =& PEAR::getStaticProperty('PEAR_Error', 'skiptrace');
$skiptrace = true;

// program service class
class TimeSerivce {
    public function now () {
        date_default_timezone_set("Europe/Berlin");
        return (date ("H:i"));
    }
}

// web service classs develop
$service = new TimeSerivce();

// server develop
$ss = new SOAP_SERVER();

// assing the name to the service
$ss->addObjectMap($service, "urn:TimeSerivce");

// Einstellung, dass POST-Daten an den Service weiter gegeben werden
// preferene to forword POST data to the service
$ss->service ($HTTP_RAW_POST_DATA);

?>


fourat dot zouari at tritux dot com 20-Jun-2009 03:08


In addition to the KeepAlive trick which is a "server-side" modification, on the "client side" default_socket_timeout should be increased from its default value (60) when you deal with ~slow SOAP servers.
As for the KeepAlive, if creating a new separate vhost for the soap api is not possible, you can add this to your existing vhost: BrowserMatch "^PHP-SOAP" nokeepalive
where PHP-SOAP is the agent name of your soap client, if you dont know what agent name your client use, just checkout the access.log of your apache.


peter dot hansen at fastit dot net 01-May-2009 01:57


When you get errors like:
"Fatal error: Uncaught SoapFault exception: [HTTP] Error Fetching http headers in"
after a few (time intensive) SOAP-Calls, check your webserver-config.

Sometimes the webservers "KeepAlive"-Setting tends to result in this error. For SOAP-Environments I recommend you to disable KeepAlive.

Hint: It might be tricky to create a dedicated vhost for your SOAP-Gateways and disable keepalive just for this vhost because for normal webpages Keepalive is a nice speed-boost.

相关推荐