PHP使用SOAP扩展实现WebService的方法


Posted in PHP onApril 01, 2016

本文实例讲述了PHP使用SOAP扩展实现WebService的方法。分享给大家供大家参考,具体如下:

最近在一个PHP项目中对接外部接口涉及到WebService,搜索引擎上相关文章不是很多,找到的大都是引用一个号称很强大的开源软件NuSOAP(下载地址:http://sourceforge.net/projects/nusoap/),即一些类。文章写描述的环境是PHP 4.3,现在都流行PHP 5.2或PHP 5.3了。先拿来试试,运行出错,原来NuSOAP提供的soapclient类与PHP 5中新增了内置的SOAP扩展的SoapClient类冲突了。

虽然NuSOAP号称可以用于所有的PHP 环境,不受服务器安全设置的影响。但需要引用一大堆类文件,还是觉得用PHP 5中新增了内置的SOAP扩展好一些,能实现实用就好。先了解一下SOAP:

一、SOAP和XML-PRC比较

在Web服务发展的初期,XML格式化消息的第一个主要用途是,应用于XML-RPC协议,其中RPC代表远程过程调用。在XML远程过程调用(XML-RPC)中,客户端发送一条特定消息,该消息中必须包括名称、运行服务的程序以及输入参数。

XML-RPC只能使用有限的数据类型种类和一些简单的数据结构。人们认为这个协议还不够强大,于是就出现了SOAP——其最初的定义是简单对象访问协议。之后,大家逐渐意识到SOAP其实并不简单,而且也不需要必须使用面向对象语言,所以,现在人们只是沿用SOAP这个名称而已。

XML-RPC只有简单的数据类型集,取而代之,SOAP是通过利用XML Schema的不断发展来定义数据类型的。同时,SOAP也能够利用XML 命名空间,这是XML-RPC所不需要的。如此一来,SOAP消息的开头部分就可以是任何类型的XML命名空间声明,其代价是在系统之间增加了更多的复杂性和不兼容性。

随着计算机行业的觉醒,人们发现了基于XML的Web服务的商业潜力,于是,各家公司开始不断地发掘想法、观点、论据以及标准化尝试。W3C曾经设法以“Web服务活动”的名义来组织成果展,其中也包括实际做出SOAP的XML协议工作组(XML Protocol Working Group)。与Web服务有关的标准化成果(从某种程度上说与SOAP相关或者依赖于SOAP)的数量已经倍增了到了令人惊讶的程度。

最初,SOAP是作为XML-RPC的扩展而发展起来的,它主要强调的是,通过从WSDL文件中所获得的方法和变量名来进行远程过程调用。现在,通过不断进步,人们发现了更多的使用SOAP的方式,而不仅仅是采用“文件”方式——基本上是使用一个SOAP信封来传送XML格式化文件。无论如何,要掌握SOAP,了解WSDL所扮演的角色是最根本的。

二、SOAP数据包结构解析

SOAP的消息被称为一个SOAP Envelope,包括SOAP Header和SOAP Body。其中,SOAP Header可以方便的插入各种其它消息来扩充Web Service的功能,比如Security(采用证书访问Web Service),SOAP Body则是具体的消息正文,也就是Marshall后的信息。

SOAP调用的时候,也就是向一个URL(比如 http://api.google.com/search/beta2 )发送HTTP Post报文(根据SOAP规范,HTTP Get报文也可被支持),调用方法的名字在HTTP Request Header SOAP-Action中给出,接下来就是SOAP Envelope了。服务端接到请求,执行计算,将返回结果Marshall成XML,用HTTP返回给客户端。

三、SOAP简单示例

SOAP开发一般有三种方式选择:

1)、PEAR自带的SOAP扩展;
2)、PHP自带的SOAP扩展;
3)、NuSOAP(纯PHP) 。

PHP 5中新增了内置的SOAP扩展,作为PHP的一部分提供的,因此不需要下载、安装和管理单独的包。这是第一个用C而不是PHP为PHP编写的SOAP实现,因此作者声称它的速度要快得多。相关文档包含在PHP手册的Function Reference部分(php_soap.dll)。

一个访问.NET WEB服务的客户端例子:

< ? php
$objSoapClient = new SoapClient("http://www.webservicemart.com/uszip.asmx?WSDL");
$param = array("ZipCode"=>'12209'); 
$out = $objSoapClient->ValidateZip($param);
$data = $out->ValidateZipResult;
echo $data;
?>

四、实例

1)、用PHP建立SOAP服务

建立soap_server.php(虚拟路径为:http://localhost/php/soap/soap_server.php)

< ? php
/**
* A simple math utility class
*/
class math{
  /**
  * Add two integers together
  *
  * @param integer $a The first integer of the addition
  * @param integer $b The second integer of the addition
  * @return integer The sum of the provided integers
  */
  public function add($a, $b){
    return $a + $b;
  }
  /**
  * Subtract two integers from each other
  *
  * @param integer $a The first integer of the subtraction
  * @param integer $b The second integer of the subtraction
  * @return integer The difference of the provided integers
  */
  public function sub($a, $b){
    return $a - $b;
  }
  /**
  * Div two integers from each other
  *
  * @param integer $a The first integer of the subtraction
  * @param integer $b The second integer of the subtraction
  * @return double The difference of the provided integers
  */
  public function div($a, $b){
    if($b == 0){
      throw new SoapFault(-1, "Cannot divide by zero!");
    }
    return $a / $b;
  }
}
$server = new SoapServer('math.wsdl', array('soap_version'=>SOAP_1_2));
$server->setClass("math");
$server->handle(); 
?>

注:

a)、math类是即将公开的webservice;
b)、$server->setClass,不是$server->addClass。
2)、用PHP客户端访问刚建立SOAP服务

< ? php
// $client = new SoapClient('http://localhost/php/soap/math.wsdl');
$client = new SoapClient("http://localhost/php/soap/soap_server.php?WSDL");
try{
  $result = $client->div(8, 2); // will cause a Soap Fault if divide by zero
  print "The answer is: $result";
}catch(SoapFault $e){
  print "Sorry an error was caught executing your request: {$e->getMessage()}";
}
?>

本质上,http://localhost/php/soap/soap_server.php?WSDL就是要访问到注释行所指的wsdl描述文件,所以这个WSDL文件必须事先生成。而对于其他语言如Java则可以动态生成。对于PHP自带的SOAP扩展要求这个WSDL文件必须事先生成好。

可以用ZendStudio生成静态的WSDL文件,此时用到math类的phpdoc作为生成WSDL的元数据。用ZendStudio生成wsdl文件时,必须正确说明Web服务目标地址,片断如下:

...
  <service name="mathService">
    <port binding="typens:mathBinding" name="mathPort">
      <soap:address location="http://localhost/php/soap/soap_server.php"></soap:address>
    </port>
  </service>
...

注:调用PHP Webserver的方法必须传入命名参数。

希望本文所述对大家PHP程序设计有所帮助。

PHP 相关文章推荐
substr()函数中文版
Oct 09 PHP
简单易用的计数器(数据库)
Oct 09 PHP
phpQuery占用内存过多的处理方法
Nov 13 PHP
PHP开发注意事项总结
Feb 04 PHP
android上传图片到PHP的过程详解
Aug 03 PHP
基于PHP代码实现中奖概率算法可用于刮刮卡、大转盘等抽奖算法
Dec 20 PHP
php代码检查代理ip的有效性
Aug 19 PHP
yii2.0数据库迁移教程【多个数据库同时同步数据】
Oct 08 PHP
THinkPHP获取客户端IP与IP地址查询的方法
Nov 14 PHP
Yii实现复选框批量操作实例代码
Mar 15 PHP
Laravel框架控制器的request与response用法示例
Sep 30 PHP
phpQuery采集网页实现代码实例
Apr 02 PHP
PHP全局变量与超级全局变量区别分析
Apr 01 #PHP
PHP计算数组中值的和与乘积的方法(array_sum与array_product函数)
Apr 01 #PHP
PHP采用超长(超大)数字运算防止数字以科学计数法显示的方法
Apr 01 #PHP
Zend Studio使用技巧两则
Apr 01 #PHP
PHP数学运算与数据处理实例分析
Apr 01 #PHP
PHP数学运算函数大汇总(经典值得收藏)
Apr 01 #PHP
PHP操作FTP类 (上传、下载、移动、创建等)
Mar 31 #PHP
You might like
同台服务器使用缓存APC效率高于Memcached的演示代码
2010/02/16 PHP
10条PHP高级技巧[修正版]
2011/08/02 PHP
thinkphp5.1 文件引入路径问题及注意事项
2018/06/13 PHP
javascript Array.remove() 数组删除
2009/08/06 Javascript
JScript 脚本实现文件下载 一般用于下载木马
2009/10/29 Javascript
jquery简单倒计时实现方法
2015/12/18 Javascript
js实现图片无缝滚动特效
2020/03/19 Javascript
Web开发中客户端的跳转与服务器端的跳转的区别
2017/03/05 Javascript
nodejs模块nodemailer基本使用-邮件发送示例(支持附件)
2017/03/28 NodeJs
vue基于Vue2.0和高德地图的地图组件实例
2017/04/28 Javascript
jquery仿微信聊天界面
2017/05/06 jQuery
vue2.0 element-ui中el-select选择器无法显示选中的内容(解决方法)
2018/08/24 Javascript
vuex actions传递多参数的处理方法
2018/09/18 Javascript
JavaScript设计模式之责任链模式实例分析
2019/01/16 Javascript
详解用Webpack与Babel配置ES6开发环境
2019/03/12 Javascript
vue生命周期与钩子函数简单示例
2019/03/13 Javascript
Vue中jsx不完全应用指南小结
2019/11/01 Javascript
node.js使用 http-proxy 创建代理服务器操作示例
2020/02/10 Javascript
vue实现给div绑定keyup的enter事件
2020/07/31 Javascript
安装Python的web.py框架并从hello world开始编程
2015/04/25 Python
Python标准库之Sys模块使用详解
2015/05/23 Python
Python Sqlite3以字典形式返回查询结果的实现方法
2016/10/03 Python
python使用Plotly绘图工具绘制气泡图
2019/04/01 Python
python将字符串转变成dict格式的实现
2019/11/18 Python
Python Django2 model 查询介绍(条件、范围、模糊查询)
2020/03/16 Python
PyTorch中model.zero_grad()和optimizer.zero_grad()用法
2020/06/24 Python
Python字典实现伪切片功能
2020/10/28 Python
Sephora丝芙兰澳洲官方网站:国际知名化妆品购物
2016/10/27 全球购物
全球度假村:Club Med
2017/11/27 全球购物
幼儿园安全检查制度
2014/01/30 职场文书
特教教师先进事迹
2014/05/21 职场文书
圣诞节活动策划方案
2014/06/09 职场文书
领导干部失职检讨书
2015/05/05 职场文书
幼儿园百日安全活动总结
2015/05/07 职场文书
2015年音乐教研组工作总结
2015/07/22 职场文书
nginx 配置缓存
2022/05/11 Servers