dynweb / zend-soap-service-provider
一个基于ZendFramwork项目的ZendSoap的SOAP服务提供者。
Requires
- silex/silex: ^2.0
- zendframework/zend-soap: ^2.6
Requires (Dev)
- pimple/pimple: dev-master
- satooshi/php-coveralls: dev-master
README
一个基于ZendFramework项目的ZendSoap组件的Silex SOAP服务提供者。
有关Zend Soap的更多信息,请查看Zend Framework文档
##为什么需要一个Zend Soap silex服务提供者?
- 为了测试
- 为了更好的集成
- 为了简单
##安装
- 在您的
composer.json
的require部分添加"dynweb/zend-soap-service-provider": "dev-master"
并运行composer install
命令。 - 注册服务:
$app->register(new ZendSoapServiceProvider());
并且不要忘记use \Ibsciss\Silex\Provider\ZendSoapServiceProvider
语句。
##用法
###基本使用
当服务提供者被注册时,您可以访问两个基本服务
- soap.server,Zend\Soap\Server 的实例
- soap.client,Zend\Soap\Client 的实例
$app = new Application(); $app->register(new ZendSoapServiceProvider()); //client method call $app['soap.client']->methodCall(); //server handling $app['soap.server']->handle();
###多个实例
如果您需要更多连接,您可以使用 soap.instances
参数定义多个实例。
//during registration $app->register(new ZendSoapServiceProvider(), array( 'soap.instances' => array( 'connection_one', 'connection_two' ) )); // --- OR --- $app->register(new ZendSoapServiceProvider()); $app['soap.instances'] = array( 'connection_one', 'connection_two' );
您可以通过以下两个服务访问您的实例
soap.clients
soap.servers
第一个定义的服务是默认服务,并通过 soap.client
和 soap.server
服务访问。
$app['soap.clients']['connection_one']; //same as $app['soap.client']; $app['soap.servers']['connection_two'];
###WSDL管理
您可以使用 soap.wsdl
参数为全局服务提供一个(可选)WSDL。
//during registration $app->register(new ZendSoapServiceProvider(), array( 'soap.wsdl' => '<wsdl></wsdl>'; )); // --- OR --- $app['soap.wsdl'] = '<wsdl></wsdl>'; $app['soap.server']->getWsdl(); //return <wsdl></wsdl>
对于多个实例,可以为特定实例定义wsdl
//during registration $app->register(new ZendSoapServiceProvider(), array( 'soap.wsdl' => '<wsdl></wsdl>', 'soap.instances' => array( 'connection_one', 'connection_two' => array('wsdl' => '<wsdl>anotherOne</wsdl>') ); )); // --- OR --- $app['soap.wsdl'] = '<wsdl></wsdl>'; $app['soap.instances'] = array( 'connection_one' 'connection_two' => array('wsdl' => '<wsdl>anotherOne</wsdl>') );
注意:如果您为每个实例提供一个wsdl,则不需要指定全局的wsdl
//if you provide one wsdl per instance you don't have to specify a global one $app->register(new ZendSoapServiceProvider(), array( 'soap.instances' => array( 'connection_one' => array('wsdl' => '<wsdl></wsdl>'), 'connection_two' => array('wsdl' => '<wsdl>anotherOne</wsdl>') ); )); $app['soap.servers']['connection_one']->getWsdl() //return <wsdl></wsdl> $app['soap.servers']['connection_two']->getWsdl() //return <wsdl>anotherOne</wsdl>
关于 \Zend\Soap 实现
该包现在使用官方的 \Zend\Soap
包
在 \Zend\Soap\Server
调试模式
当您的代码中抛出异常时,\Zend\Soap\Server
会捕获它并检查是否是授权的异常。如果不是,出于安全原因,它会发送一个“未知错误”消息。在生产环境中这是一种合理的做法,但在开发测试过程中这会非常令人烦恼。
因此,服务提供者扩展了 Server
类以添加一个 debugMode
方法,当 silex 的 debug
选项为 true
时自动激活(通过 setDebugMode($boolean)
服务器方法提供手动启用/禁用调试模式)。例如
//enable: $app['soap.server']->setDebugMode(true); //disable: $app['soap.server']->setDebugMode(false);
在调试模式下,服务器将所有异常发送到 soap 客户端。
异常管理
如上所述,当异常被 Zend\Soap\Server
捕获时,错误消息变为“未知错误”。因此,即使您将异常写入日志,也无法确定故障的根本原因,为了避免这种麻烦,提供者在其服务器类中提供了一个 getException
方法。例如
$app['soap.server']->fault(new \Exception('test')); $app['soap.server']->getException(); //return the Exception instance given as attribute to the fault method.
内部 '\SoapServer' 实例
Zend\Soap\Server
使用内部 \SoapServer
实例来处理请求。在某些情况下,您需要访问此实例(例如,当 setReturnResponse
设置为 true 时发送 SoapFault)。这就是为什么提供者添加了一个 getSoap()
方法,该方法提供当前内部 \SoapServer
实例。例如
$app['soap.server']->getSoap()->fault(new \SoapFault('an error occured'));
##高级主题
###更改Soap类
如果您想使用您自己的个人soap类,或者为了测试目的,您可以使用 soap.client.class
和 soap.server.class
覆盖 soap、服务器或客户端类。
警告:如果您处于 dotNet 模式,您必须使用 soap.client.dotNet.class
(或 client.dotNet.class
用于实例覆盖)。
//global level $app->register(new ZendSoapServiceProvider()); $app['soap.server.class'] = '\stdClass'; $app['soap.client.class'] = '\stdClass'; $app['soap.client']; //instanceOf stdClass; $app['soap.server']; //instanceOf stdClass; //---------------- //you can also override at the instance scope $app = new Application(); $app->register(new ZendSoapServiceProvider(), array( 'soap.instances' => array( 'connection_one' => array('server.class' => '\stdClass'), 'connection_two' => array('client.class' => '\stdClass') ) )); $app['soap.clients']['connection_one']; //instanceOf Zend\Soap\Client $app['soap.servers']['connection_one']; //instanceOf stdClass $app['soap.clients']['connection_two']; //instanceOf stdClass $app['soap.servers']['connection_two']; //instanceOf Zend\Soap\Server
###更改Soap版本
您可以使用 soap.version
属性来指定 SOAP 版本。允许的值有
- SOAP_1_1
- SOAP_1_2(默认值)
$app->register(new ZendSoapServiceProvider(), array( 'soap.version' => SOAP_1_1 )); // ----- OR ----- $app['soap.version'] = SOAP_1_1; //results : $app['soap.client']->getSoapVersion(); // SOAP_1_1; $app['soap.server']->getSoapVersion(); // SOAP_1_1; // ----------------------- //like others options, you can define it at the instance level : $app->register(new ZendSoapServiceProvider(), array( 'soap.instances' => array( 'connection_one' => array('version' => SOAP_1_1), 'connection_two' => array('dotNet' => true), 'connection_three' ) )); $app['soap.clients']['connection_one']->getSoapVersion(); // SOAP_1_1 $app['soap.servers']['connection_one']->getSoapVersion(); // SOAP_1_1 //dotNet use 1.1 by default; $app['soap.clients']['connection_two']->getSoapVersion(); // SOAP_1_1 $app['soap.servers']['connection_two']->getSoapVersion(); // SOAP_1_2 //default config $app['soap.clients']['connection_three']->getSoapVersion(); // SOAP_1_2 $app['soap.servers']['connection_three']->getSoapVersion(); // SOAP_1_2
###DotNet 特定模式
DotNet 框架在处理 SOAP 参数方面与 PHP 或 Java 实现略有不同。
因此,如果您必须将 SOAP 网络服务与 DotNet 服务器集成,请将 soap.dotNet
选项设置为 true
。
$app['soap.dotNet'] = true; $app['soap.client'] // instanceOf Zend\Soap\Client\DotNet //you can also define it at the instance scope $app->register(new ZendSoapServiceProvider(), array( 'soap.instances' => array( 'connection_one' => array('dotNet' => true), 'connection_two' ) )); $app['soap.clients']['connection_one']; //instanceOf Zend\Soap\Client\DotNet $app['soap.clients']['connection_two']; //instanceOf Zend\Soap\Client
如果您想覆盖 DotNet 类,请使用 soap.client.dotNet.class
属性代替 soap.client.class
。
##总结
###服务
- soap.client:默认 SOAP 客户端实例,是第一个定义的实例的别名
- soap.server:默认 SOAP 服务器实例,是第一个定义的实例的别名
- soap.clients:SOAP 客户端实例容器
- soap.servers:SOAP 服务器实例容器
###参数
- soap.wsdl:全局 wsdl
- soap.client.class:覆盖客户端工厂类
- soap.server.class:覆盖服务器工厂类
- soap.dotNet:启用 DotNet 模式,使用 Soap\Client\DotNet 类
- soap.client.dotNet.class:在 DotNet 模式下覆盖客户端工厂类
- soap.version:定义 SOAP 版本,接受常量 SOAP_1_1 或 SOAP_1_2 作为值(默认为 SOAP_1_2,除非在 DotNet 模式下)
所有参数都可以在实例级别进行定义
$app['soap.instances'] = array( 'connection_two' => array( 'wsdl' => '<wsdl>anotherOne</wsdl>', 'client.class' => '\stdClass', 'server.class' => '\stdClass', 'dotNet' => true, 'client.dotNet.class' => '\stdClass', 'version' => SOAP_1_1 ) );