大家好,上一篇我们聊到基本的概念。相信大家总体也有个认识。接下来我们讲一下服务的搭建。
首先,我们要安装php_soap这个扩展。怎么安装呢!请查看我以前写的安装扩展的文章。
在macos系统上安装php环境和扩展等
安装成功后 php -m 查看
一、服务端开发
创建Service.php,构建服务端
<?php
//Service类
class Service {
//方法
public function HelloWorld() {
return "Hello";
}
public function Add($a, $b) {
return $a + $b;
}
}
//echo "==========";exit;
//自动生成的文件
$file = "Service.wsdl";
if(file_exists($file))
{
$server = new SoapServer('Service.wsdl', array('soap_version' => SOAP_1_2)); ##此处的Service.wsdl文件是上面生成的
//echo "=========";exit;
$server->setClass("Service"); //注册Service类的所有方法
//$server->addFunction('HelloWorld');
$server->handle(); //处理请求
}
else
{
//创建wsdl文件
require_once './SoapDiscovery.class.php';
// 创建WSDL
$disco = new SoapDiscovery('Service','Solsoft_Store');
header("Content-type: text/xml");
if (isset($_SERVER['QUERY_STRING']) && strcasecmp($_SERVER['QUERY_STRING'],'wsdl')==0) {
echo $disco->getWSDL();
}else {
echo $disco->returnWSDL();
}
}
?>
二、客户端开发
创建client.php,构建客户端
<?php
error_reporting(E_ERROR);
ini_set("display_errors","Off");
//require_once ("STD3Des.class.php");
//require_once ("doubei_rsa.function.php");
ini_set('soap.wsdl_cache_enabled', "0"); //关闭wsdl缓存
header("application/soap+xml; charset=utf-8");
try {
//libxml_disable_entity_loader(false);
$client = new SoapClient("http://doubei.gzy/Tptest/soap/Wsdl/Store.php?wsdl");
var_dump( $client->__getFunctions() );//array(2) { [0]=> string(19) "string HelloWorld()" [1]=> string(32) "string Add(string $a, string $b)" }
print_r($client->HelloWorld());//Hello
} catch (SOAPFault $e) {
print $e;
}
?>
三、我们怎么样,生成一个wsdl文件呢!我google了一下。对于php来说。也就两种方式。
1、下载Zend Studio 软件,这个软件可以。
2、下载SoapDiscovery.class.php这个类文件。
我是使用的第二种方式。附上代码:
<?php
/**
* @package SoapDiscovery 核心
* @author gongzhiyang
* @copyright Copyright (c) 2018
* @access public
**/
class SoapDiscovery {
private $class_name = '';
private $service_name = '';
/**
* SoapDiscovery::__construct() SoapDiscovery class Constructor.
*
* @param string $class_name
* @param string $service_name
**/
public function __construct($class_name = '', $service_name = '') {
$this->class_name = $class_name;
$this->service_name = $service_name;
}
/**
* 获取WSDL
*
* @return string
**/
public function getWSDL() {
if (empty($this->service_name)) {
throw new Exception('No service name.');
}
$headerWSDL = "<?xml version=\"1.0\" ?>\n";
$headerWSDL.= "<definitions name=\"$this->service_name\" targetNamespace=\"urn:$this->service_name\" xmlns:wsdl=\"http://schemas.xmlsoap.org/wsdl/\" xmlns:soap=\"http://schemas.xmlsoap.org/wsdl/soap/\" xmlns:tns=\"urn:$this->service_name\" xmlns:xsd=\"http://www.w3.org/2001/XMLSchema\" xmlns:SOAP-ENC=\"http://schemas.xmlsoap.org/soap/encoding/\" xmlns=\"http://schemas.xmlsoap.org/wsdl/\">\n";
$headerWSDL.= "<types xmlns=\"http://schemas.xmlsoap.org/wsdl/\" />\n";
if (empty($this->class_name)) {
throw new Exception('No class name.');
}
$class = new ReflectionClass($this->class_name);
if (!$class->isInstantiable()) {
throw new Exception('Class is not instantiable.');
}
$methods = $class->getMethods();
$portTypeWSDL = '<portType name="'.$this->service_name.'Port">';
$bindingWSDL = '<binding name="'.$this->service_name.'Binding" type="tns:'.$this->service_name."Port\">\n<soap:binding style=\"rpc\" transport=\"http://schemas.xmlsoap.org/soap/http\" />\n";
$serviceWSDL = '<service name="'.$this->service_name."\">\n<documentation />\n<port name=\"".$this->service_name.'Port" binding="tns:'.$this->service_name."Binding\"><soap:address location=\"http://".$_SERVER['SERVER_NAME'].':'.$_SERVER['SERVER_PORT'].$_SERVER['PHP_SELF']."\" />\n</port>\n</service>\n";
$messageWSDL = '';
foreach ($methods as $method) {
if ($method->isPublic() && !$method->isConstructor()) {
$portTypeWSDL.= '<operation name="'.$method->getName()."\">\n".'<input message="tns:'.$method->getName()."Request\" />\n<output message=\"tns:".$method->getName()."Response\" />\n</operation>\n";
$bindingWSDL.= '<operation name="'.$method->getName()."\">\n".'<soap:operation soapAction="urn:'.$this->service_name.'#'.$this->class_name.'#'.$method->getName()."\" />\n<input><soap:body use=\"encoded\" namespace=\"urn:$this->service_name\" encodingStyle=\"http://schemas.xmlsoap.org/soap/encoding/\" />\n</input>\n<output>\n<soap:body use=\"encoded\" namespace=\"urn:$this->service_name\" encodingStyle=\"http://schemas.xmlsoap.org/soap/encoding/\" />\n</output>\n</operation>\n";
$messageWSDL.= '<message name="'.$method->getName()."Request\">\n";
$parameters = $method->getParameters();
foreach ($parameters as $parameter) {
$messageWSDL.= '<part name="'.$parameter->getName()."\" type=\"xsd:string\" />\n";
}
$messageWSDL.= "</message>\n";
$messageWSDL.= '<message name="'.$method->getName()."Response\">\n";
$messageWSDL.= '<part name="'.$method->getName()."\" type=\"xsd:string\" />\n";
$messageWSDL.= "</message>\n";
}
}
$portTypeWSDL.= "</portType>\n";
$bindingWSDL.= "</binding>\n";
$fso = fopen($this->class_name . ".wsdl" , "w");
fwrite($fso, sprintf('%s%s%s%s%s%s', $headerWSDL, $portTypeWSDL, $bindingWSDL, $serviceWSDL, $messageWSDL, '</definitions>'));
//返回一个格式化字符串
return sprintf('%s%s%s%s%s%s', $headerWSDL, $portTypeWSDL, $bindingWSDL, $serviceWSDL, $messageWSDL, '</definitions>');
//$fso = fopen($this->class_name . ".wsdl" , "w");
//if(fwrite($fso, sprintf('%s%s%s%s%s%s', $headerWSDL, $portTypeWSDL, $bindingWSDL, $serviceWSDL, $messageWSDL, '</definitions>'))) return $this->returnWSDL(); else return "flase";
}
/**
* 返回 WSDL
*
* @return string
**/
public function returnWSDL() {
return "<?xml version=\"1.0\" ?>\n<disco:discovery xmlns:disco=\"http://schemas.xmlsoap.org/disco/\" xmlns:scl=\"http://schemas.xmlsoap.org/disco/scl/\">\n<scl:contractRef ref=\"http://".$_SERVER['SERVER_NAME'].':'.$_SERVER['SERVER_PORT'].$_SERVER['PHP_SELF']."?wsdl\" />\n</disco:discovery>";
}
}
?>
Service.wsdl 文件
<?xml version="1.0" ?>
<definitions name="soap" targetNamespace="urn:soap" xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/" xmlns:soap="http://schemas.xmlsoap.org/wsdl/soap/" xmlns:tns="urn:soap" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:SOAP-ENC="http://schemas.xmlsoap.org/soap/encoding/" xmlns="http://schemas.xmlsoap.org/wsdl/">
<types xmlns="http://schemas.xmlsoap.org/wsdl/" />
<portType name="soapPort"><operation name="HelloWorld">
<input message="tns:HelloWorldRequest" />
<output message="tns:HelloWorldResponse" />
</operation>
<operation name="Add">
<input message="tns:AddRequest" />
<output message="tns:AddResponse" />
</operation>
</portType>
<binding name="soapBinding" type="tns:soapPort">
<soap:binding style="rpc" transport="http://schemas.xmlsoap.org/soap/http" />
<operation name="HelloWorld">
<soap:operation soapAction="urn:soap#Service#HelloWorld" />
<input><soap:body use="encoded" namespace="urn:soap" encodingStyle="http://schemas.xmlsoap.org/soap/encoding/" />
</input>
<output>
<soap:body use="encoded" namespace="urn:soap" encodingStyle="http://schemas.xmlsoap.org/soap/encoding/" />
</output>
</operation>
<operation name="Add">
<soap:operation soapAction="urn:soap#Service#Add" />
<input><soap:body use="encoded" namespace="urn:soap" encodingStyle="http://schemas.xmlsoap.org/soap/encoding/" />
</input>
<output>
<soap:body use="encoded" namespace="urn:soap" encodingStyle="http://schemas.xmlsoap.org/soap/encoding/" />
</output>
</operation>
</binding>
<service name="soap">
<documentation />
<port name="soapPort" binding="tns:soapBinding"><soap:address location="http://doubei.gzy:80/Tptest/soap/Wsdl/creat_wsdl.php" />
</port>
</service>
<message name="HelloWorldRequest">
</message>
<message name="HelloWorldResponse">
<part name="HelloWorld" type="xsd:string" />
</message>
<message name="AddRequest">
<part name="a" type="xsd:string" />
<part name="b" type="xsd:string" />
</message>
<message name="AddResponse">
<part name="Add" type="xsd:string" />
</message>
</definitions>
参考文献:
http://www.php.net/manual/en/book.soap.php
已上就是一个简单的搭建,大家可以试一下。下一节我们聊一下我们公司的项目,可以加深一些认识。谢谢大家!