嗯,又找到一些好玩的东西,web service。
有个叫Nusoap类,在php4下比较流行。但是淡水这次玩的是php5,所以他就没戏了。
先恶补一下相关知识。
先要打开php5的web service扩展。linux下,嗯,好像不会-_-!。windows下,把php.ini文件中 extension=php_soap.dll 去掉注释即可。
方法:
SoapClient->__soapCall()
说明:
class SoapClient {
mixed __soapCall ( string function_name, array arguments [, array options [, mixed input_headers [, array &output_headers]]])
}
In WSDL mode, you can simply call SOAP functions as SoapClient methods. This method useful in non-WSDL mode when soapaction is unknown, uri differs from the default or when sending and/or receiving SOAP Headers
返回值:
一个简单类型的返回值,或是一个关联数组
例子:

<?php
 
$client = new SoapClient("some.wsdl");
$client->SomeFunction($a, $b, $c);
 
$client->__soapCall("SomeFunction",
                    
array($a, $b, $c)
                    
);
$client->__soapCall("SomeFunction",
                    
array($a, $b, $c),
                    
NULL,
                    
new SoapHeader(),
                    
$output_headers
                    
);
 
 
$client = new SoapClient(null, array('location' => "http://localhost/soap.php",'uri'=> "http://test-uri/"));
$client->SomeFunction($a, $b, $c);
$client->__soapCall("SomeFunction",
                    
array($a, $b, $c)
                    
);
$client->__soapCall("SomeFunction",
                    
array($a, $b, $c),
                    
array('soapaction' => 'some_action','uri' => 'some_uri')
                    
);
?>

1.in WSDL mode
soapCall应用web service,例子用的是asp.net的web service,提供service.asmx页面,调用及查看都比较简单,手册上的example也大多是这个类型,比较简单.

SOAP发送的协议:

POST /servicepath/service.asmx HTTP/1.1
Host: 211.186.1.4
Content-Type: text/xml; charset=utf-8
Content-Length: length
SOAPAction: “http://211.186.5.15/Service/ServiceMethod”

<?xml version="1.0" encoding="utf-8"?>
<soap:Envelope xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
 
<soap:Body>
    
<ServiceMethod xmlns="http://211.186.5.15/Service">
      
<param1>string</param1>
      
<param2>string</param2>
      
<param3>string</param3>
    
</ServiceMethod>
 
</soap:Body>
</soap:Envelope>

调用方法:

<?php
$client = new SoapClient("http://www.xxx.com/service/service.asmx?WSDL");
//向SOAP服务方发送参数值
$param1 = "p1";
$param2 = "p2";
$param3 = "p3";
 
//serviceParam1,serviceParam2,serviceParam3为发送参数值所对应的参数名(或service端提供的字段名)
$param = array('serviceParam1' => $param1,'serviceParam2' => $param2,'serviceParam3' => $param3);
 
//默认以parameters字段标示传递的参数数组(这里的web services是.net提供的,所以和php提供的Web service不同)
$arr = $client->__soapCall('ServiceMethod',array('parameters' => $param));
//这里淡水推荐直接使用web services提供的方法,如
//$arr = $client->ServiceMethod($param);
 
print_r($arr);
?>

2.in non-WSDL mode
这种情况下soapaction is unknown

SOAP发送协议:

POST /services/SoapMethod?WSDL HTTP/1.1
Host: 220.211.1.12:8088
Connection: Keep-Alive
User-Agent: PHP-SOAP/5.2.5
Content-Type: text/xml; charset=utf-8
SOAPAction: “urn:SoapMethod#ServiceMethod”
Content-Length: 1297

<?xml version="1.0" encoding="UTF-8"?>
<SOAP-ENV:Envelope xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/" xmlns:ns1="urn:SoapMethod" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:SOAP-ENC="http://schemas.xmlsoap.org/soap/encoding/" xmlns:ns2="http://220.211.1.12" SOAP-ENV:encodingStyle="http://schemas.xmlsoap.org/soap/encoding/">
<SOAP-ENV:Body>
<ns1:ServiceMethod>
<ServiceMethodSection xsi:type="ns2:ServiceObjectType">
<param1 xsi:type="xsd:string">01019</param1>
<param2 xsi:type="xsd:long">10</param2>
<param3 xsi:type="xsd:long">0</param3>
<param4 xsi:type="xsd:long">11</param4>
</ServiceMethodSection>
</ns1:ServiceMethod>
</SOAP-ENV:Body>
</SOAP-ENV:Envelope>

调用方法:

<?php
//传递一个参数
try {
      
$client = new SoapClient(
                      
null,
                      
array('location' => 'http://192.168.1.180:8088/services/SoapPage?WSDL','uri' => 'http://192.168.1.180:8088/services/')
                      
);   
      
$result$client->__soapCall('ServiceMethod', array('fieldName' => "data")); //以数组形式传递params
      
//$result =  $client->__soapCall('ServiceMethod', array(new SoapParam("data", 'fieldName')));  //以构造服务端参数的形式构造参数传递给服务端 
      
var_dump($result);
 
}
 
catch (Exception $e)
 
{
      
printf("Message = %s",$e->__toString());
 
}
?>

附注一下:
class SoapParam {
__construct ( mixed data, string name )
}
参数:
data
The data to pass or return. You can pass this parameter directly as PHP value, but in this case it will be named as paramN and the SOAP Service may not understand it.

name
参数名

<?php
//传递多个参数:
//如果服务端在non wsdl的情况下要求传递一个对象参数,该对象中包含多个属性,则
 
try {
      
$client = new SoapClient(
                      
null,
                      
array('location' => 'http://192.168.1.180:8088/services/SoapPage?WSDL','uri' => 'urn:SoapName')
                      
);//uri部分也可能是uri地址
 
      
class Obj{
      
public $param1 = '01019';
      
public $param2 = 10;
      
public $param3 = 0;
      
public $param4 = 11;
      
}
 
    
$struct = new Obj()//创建服务端要求传递的对象
    
//如果服务端变态到传递的参数有的参数类型是你编程语言中没有的数据类型,
    
//如php,没有Java的Long类型(一般web service考虑通用性,数据类型都是string或int型)
    
//就要将参数进行强制类型转换
    
//这样的处理也只是在SOAP传输中将xml的参数类型替换成服务端所要求的类型名
    
//并不是真实转化传递的数据类型
    
$struct->param1 = iconv('gb2312','utf-8',$struct->param1);
    
$struct->param2 = new SoapVar($struct->param2,XSD_LONG);
    
$struct->param3 = new SoapVar($struct->param3,XSD_LONG);
    
$struct->param4 = new SoapVar($struct->param4,XSD_LONG);
 
    
//序列化对象中使用SoapVar的方法参考php手册对SoapVar的解释,每个参数都解释的很清楚
    
$soapstruct = new SoapVar($struct, SOAP_ENC_OBJECT, "ServiceObjectType", "http://soapinterop.org/xsd"); //对象序列化,注意区分,SOAP对象的序列化不是用serialize
    
      
$result$client-> ServiceMethod(new SoapParam($soapstruct, 'ServiceMethodSection'));
    
//$result =  $client->__soapCall('ServiceMethod', array(new SoapParam($soapstruct, 'ServiceMethodSection')));
    
      
var_dump($result);
 
} catch (Exception $e) {
      
printf("Message = %s",$e->__toString());
 
}
?>