PHP SOAP: how can I return objects from PHP using SOAP?

I need to send / return objects or an array to / from PHP using SOAP. Any good links?

0
source share
4 answers

I use Zend_Soap_Server and Zend_Soap_Client. I send / receive an array of complex structure.

First create a class with the structure you want to get.

<?php /** * Information about people */ class PeopleInformation { /** * Name of ... * * @var string */ public $name; /** * Age of * @var int */ public $age; /** * Array of family * * @var FamilyInformation[] */ public $family; } /** * Information about his family */ class FamilyInformation { /** * Mother/sister/bro etc * * @var string */ public $relation; /** * Name * @var string */ public $name; } ?> 

Then create a service to get this data:

 <?php /** * Service to receive SOAP data */ class SoapService { /** * * @param PeopleInformation $data * @return string */ public function getUserData($data) { //here $data is object of PeopleInformation class return "OK"; } } ?> 

Now create an instance of Zend_Soap_Server in the controller at the URL http: // ourhost / soap / :

 <?php //disable wsdl caching ini_set('soap.wsdl_cache_enabled', 0); ini_set('soap.wsdl_cache', 0); $wsdl = $_GET['wsdl']; //this generate wsdl from our class SoapService if (!is_null($wsdl)) { $autodiscover = new Zend_Soap_AutoDiscover('Zend_Soap_Wsdl_Strategy_ArrayOfTypeSequence'); $autodiscover->setClass('SoapService'); $autodiscover->handle(); } //handle all soap request else { $wsdlPath = 'http://ourhost/soap/?wsdl'; $soap = new Zend_Soap_Server($wsdlPath, array( 'cache_wsdl' => false )); $soap->registerFaultException('Zend_Soap_Server_Exception'); $soap->setClass('SoapService'); $soap->handle(); } ?> 

And now you get wsdl (http: // ourhost / soap /? Wsdl) with your structure and processing request in SoapService :: getUserData. The input parameter in this method is an object of the PeopleInformation class.

+2
source

Basically, you need to create a class map and pass it to the client with soap. Yes, it’s a pain. Usually I have a method that matches the name of a Soap object with PHP objects (i.e. Person => MY_Person ) and encodes only the ones I need manually ( createdOn => DateTime ).

 class MY_WSHelper { protected static $ws_map; public static function make_map() { if( ! self::$ws_map) { self::$ws_map = array(); //These will be mapped dynamically self::$ws_map['Person'] = NULL; self::$ws_map['Animal'] = NULL; //Hard-coded type map self::$ws_map['createdOn'] = DateTime; self::$ws_map['modifiedOn'] = DateTime; foreach(self::$ws_map as $soap_name => $php_name) { if($php_name === NULL) { //Map un-mapped SoapObjects to PHP classes self::$ws_map[$soap_name] = "MY_" . ucfirst($soap_name); } } } return self::$ws_map; } } 

Client:

 $client = new SoapClient('http://someurl.com/personservice?wsdl', array('classmap' => MY_WSHelper::make_map())); $aperson = $client->getPerson(array('name' => 'Bob')); echo get_class($aperson); //MY_Person echo get_class($aperson->createdOn); //DateTime 

http://php.net/manual/en/soapclient.soapclient.php

+1
source

Dad Google points me to this Zend article with a lot of good examples on both the client and server aspects of working with soap (in particular PHP5). Looks like a good starting point.

If you are somewhat like me and cringed at the thought of writing WSDL manually, I would recommend using WSHelper , which uses the PHP reflection classes to dynamically create WSDL for you. Definitely time-saving

0
source

I repeat to share my (bad) experience.

I created a web service using PHP ZendFramework2 (ZF2).

The server responds with objects and an array of objects, and until it was accepted as input, it worked well. I used the ArrayOfTypeComplex strategy.

 $_strategy = new \Zend\Soap\Wsdl\ComplexTypeStrategy\ArrayOfTypeComplex(); 

When I try to use an array of strings as input, I felt in a dark and miserable valley until I found Ramil's answer, so I change my strategy and everything works correctly!

 $_strategy = new \Zend\Soap\Wsdl\ComplexTypeStrategy\ArrayOfTypeSequence(); if (isset($_GET['wsdl'])) { $autodiscover = new \Zend\Soap\AutoDiscover($_strategy); $autodiscover->setBindingStyle(array('style' => 'document')); $autodiscover->setOperationBodyStyle(array('use' => 'literal')); $autodiscover->setClass('Tracker\Queue\Service') ->setUri($_serverUrl); echo $autodiscover->toXml(); } 
0
source

Source: https://habr.com/ru/post/1302044/


All Articles