1. web service普及: Webservice soap wsdl差别之个人见解
Web Service实现业务诉求: Web Service是真正“办事”的那个,提供一种办事接口的统称。
WSDL提供“能办的事的文档说明”: 对要提供的服务的一种描写叙述格式。我想帮你的忙,可是我要告诉你我都能干什么,以及干这些事情须要的參数类型。
SOAP提供“请求”的规范: 向服务接口传递请求的格式,包含方法和參数等。你想让人家办事,总得告诉人家你想干什么吧,SOAP就是定义这个“请求”的格式的,依照SOAP定义的“请求”格式“书写”请求就行保证Web Service可以正确的解读你想让它干什么以及你为它提供了什么參数。在这个请求中,你须要描写叙述的主要问题有:向哪个Web Service发送请求,请求的參数类型、參数值、返回值类型。这些都“填写”完毕,也就完毕了符合SOAP规范的SOAP消息。
wsdl和soap尽管是web service的两大标准,可是两者并没有必定的联系,都能够独立使用。
wsdl提供了一个统一的接口,眼下已经成为一个国际上公认的标准,通过wsdl提供的接口能够訪问不同类型的资源(如java、c#、C、C、C++等),由于wsdl是基于xml,与语言平台无关的。另外wsdl提供了binding和service元素,用以绑定接口到详细的服务,实现了接口与实现的分离。
soap(简单对象訪问协议)是一种基于http的传输协议,用来訪问远程服务
wsdl与soap的关系在于:wsdl绑定服务的时候能够设定使用的协议,协议能够是soap、http、smtp、ftp等不论什么一种传输协议,除此以外wsdl还能够绑定jms、ejb及local java等等,只是都是须要对binding和service元素做扩展的,并且须要扩展server的功能以支持这样的扩展
soap协议是一种请求和应答协议规范,而http是web传输协议,soap的传输是能够基于http的,但也能够基于其它的传输协议,如ftp、smtp等。
简单对象訪问协议(SOAP)是W3C组织的一个Note, 它描写叙述了一种在分散的或分布式的环境中怎样交换信息的轻量级协议。SOAP是一个基于XML的协议,它包含三个部分:SOAP封装(Envelop),封装定义了一个描写叙述消息中的内容是什么,是谁发送的,谁应当接受并处理它以及怎样处理它们的框架;SOAP编码规则(Encoding Rules),用于表示应用程序须要使用的数据类型的实例;SOAP RPC表示(RPC Representation),表示远程过程调用和应答的协定;SOAP能够和多种传输协议绑定(Binding),使用底层协议交换信息。在这个文档中,眼下仅仅定义了SOAP怎样和HTTP以及HTTP扩展进行绑定的框架。
SOAP是个通信协议, SOAP在HTTP协议的基础上,把编写成XML的REQUEST參数, 放在HTTP BODY上提交个WEB SERVICEserver(SERVLET,ASP什么的) 处理完毕后,结果也写成XML作为RESPONSE送回用户端, 为了使用户端和WEB SERVICE能够相互相应,能够使用WSDL作为这样的通信方式的描写叙述文件,利用WSDL工具能够自己主动生成WS和用户端的框架文件,SOAP具备把复杂对象序列化捆绑到XML里去的能力。
SOAP的前身是RPC, 就是远程呼叫处理的协议,这个协议安全性不是非常好,多数防火墙都会阻挡RPC的通信包,而SOAP则使用HTTP协议作为主要的协议,使用port80使得SOAP能够透过防火墙,完毕RPC的功能。
SOAP协议和HTTP协议一样,都是底层的通信协议,仅仅是请求包的格式不同而已,SOAP包是XML格式的,如今我们编写WEB SERVICE不须要深入理解SOAP也没关系。假设SERVICE和CLIENT在相同的环境下使用SOAP,因为普通情况下都有自己主动生成SOAP程序框架的工具,因此不知道细节也没关系. 但是, 假设CLIENT和SERVICE的环境不同,比方说JAVA的Client和.NET的SERVICE进行通信,或者是VB CLIENT和TOMCAT下的JAVA SERVICE通信,还是要知道一点细节为好. 特别是, WSDL或者UDDI都不是标准,假设不让用就仅仅好手工配制SOAP MESSAGE啦。
2. 使用类 "SoapDiscovery.class.php" 生成wsdl文档!
SOAP类型的接口
无关编程语言、无关平台、扩展性非常好
要实现一个SOAP 型的接口,有两种方式:一种有WSDL文件方式、一中无WSDL文件方式!
对于热爱研究型的人来说,使用第一种方式能够让你清楚的了解PHP是怎么创建了一个Web Service!但第一种对于新手来说,创建一个XML格式的WSDL文件,是比較难的,这你的先了解熟悉什么是XML!学会XML语法!但对于一个急于解决这个问题的人来说!没有这么多的时间去熟悉!所以这是件烦恼的事!只是不急,上面说了,另一种无需WSDL文件的方式!并且,本解说还提供了一个自己主动生成WSDL文件的类!
解说前,先配置下PHP的soap环境支持:
找到php.ini文件
;extension=php_soap.dll
删除掉";" ,重新启动apacheserver
一、有WSDL文件方式
在这里先介绍标准的webservice。 那么怎样创建wsdl呢?对于PHP来说这确实是件非常不easy的事情,有人说用zend studio创建非常方便,这是一种方法。但对于那些不喜欢用zend studio的人来说,会认为创建一个web service还要安装zend studio,太强人所难了。
在这里介绍一个简单的方法,到网上下载SoapDiscovery.class.php类(我本地有下载的),里面有个公用方法:getWSDL(),这种方法末尾是用的return语句,那么,你改动一下这种方法:
//return sprintf('%s%s%s%s%s%s', $headerWSDL, $portTypeWSDL, $bindingWSDL, $serviceWSDL, $messageWSDL, '</definitions>');
//生成wsdl文件,将上面的return凝视去掉,那么
$fso = fopen($this->class_name . ".wsdl" , "w");
fwrite($fso, sprintf('%s%s%s%s%s%s', $headerWSDL, $portTypeWSDL, $bindingWSDL, $serviceWSDL, $messageWSDL, '</definitions>'));
如今生成wsdl的类有了,SoapDiscovery.class.php(源代码在最末尾)。
再准备一个提供服务的Service.php类文件或者函数就能够创建wsdl了!
<?php
class Service {
public function HelloWorld() {
return "Hello";
}
public function Add($a, $b) {
return $a + $b;
}
}
?>
以下创建wsdl文件的creat_wsdl.php
<?php
include("Service.php");
include("SoapDiscovery.class.php");
$disc = new SoapDiscovery('Service', 'soap'); //第一个參数是类名(生成的wsdl文件就是以它来命名的,比如:以下的Service.wsdl),即Service类,第二个參数是服务的名字(这个能够随便写)
$disc->getWSDL();
##说明:通过查看"SoapDiscovery.class.php"文件的源代码发现,此成员函数假设开启return语句,会返回一个xml格式的字符串,假设用 $strXML = $disc->getWSDL();echo $strXML;那么在浏览器中将不能显示xml的wsdl文件。由于浏览器默认用的是"html/text"来返回stdout的内容,须要在php脚本的头部用:
header("Content-type: text/html; charset=utf-8"); 才干够让浏览器不把输出作为html而是作为xml来解析!
用web訪问的方式执行create_wsdl.php文件,此时会生成一个Service.wsdl的文件,以下将会用到这个文件!
注意:上面方法生成的wsdl文件在windows以下没问题,可是在Linux以下的wsdl文件里的"location=XXX" 段,确实没有serverIP地址。所以要改动该代码中的: $_SERVER['SERVER_NAME'] 为 $_SERVER['SERVER_HOST'] ,由于在linux(nginx)以下,前者变量为空,这样才干生成正确的wsdl文档!
再在Service.php文件里加入�一些代码
<?php
class Service {
public function HelloWorld() {
return "Hello";
}
public function Add($a, $b) {
return $a + $b;
}
}
$server = new SoapServer('Service.wsdl', array('soap_version' => SOAP_1_2)); ##此处的Service.wsdl文件是上面生成的
$server->setClass("Service"); //注冊Service类的全部方法
$server->handle(); //处理请求
?>
创建webservice客户端程序,測试webservice是否有效,文件名称是:client.php
将下面内容拷贝进去:
<?php
ini_set('soap.wsdl_cache_enabled', "0"); //关闭wsdl缓存
$soap = new SoapClient('http://localhost/Dragon/soap/Service.php?wsdl');
echo $soap->Add(28, 2);
echo $soap->__soapCall('Add',array(28,2))//或这样调用
#echo $soap->__Call('Add',array(28,2));
?>
OK!測试通过!
二、无WSDL文件方式
server端
<?php
class Service
{
public function HelloWorld()
{
return "Hello";
}
public function Add($a,$b)
{
return $a+$b;
}
}
$server=new SoapServer(null,array('uri' => "abcd"));
$server->setClass("Service");
$server->handle();
?>
client
<?php
try {
$soap = new SoapClient(null, array(
"location" => "http://localhost/Dragon/soap/Service.php",
"uri" => "abcd", //资源描写叙述符server和client必须相应
"style" => SOAP_RPC,
"use" => SOAP_ENCODED
));
echo $soap->Add(12, 2);
} catch (Exction $e) {
echo print_r($e->getMessage(), true);
}
?>