views:

475

answers:

3

I am using PHP 5.2.10 and I am trying to consume a webservice which returns complex data types using the standard SOAP extension.

The problem is that SoapClient does not populate objects which are nested into other objects / array of objects. A simplified example of what I get when I call the getUtente method, specifying "my_unique_id" as a parameter is:

stdClass Object
(
    [getUtenteReturn] => stdClass Object
        (
            [userName] => my_unique_id
            [fieldOne] => ...
            [fieldTwo] => ...
            [utilizzatore] => stdClass Object
                ( // This is EMPTY instead of containing a series of userName's
                )

        )

)

The relevant part of the WDSL description is:

<element name="getUtenteResponse">
  <complexType>
    <sequence>
      <element name="getUtenteReturn" type="tns1:Cliente"/>
    </sequence>
  </complexType>
</element>
...
<complexType name="Utilizzatore">
  <sequence>
    <element name="userName" nillable="true" type="xsd:string"/>
  </sequence>
</complexType>
...
<complexType name="Cliente">
  <complexContent>
    <extension base="tns1:Utilizzatore">
      <sequence> 
        <element name="fieldOne" nillable="true" type="xsd:string"/>
        <element name="fieldTwo" nillable="true" type="xsd:string"/>
        <element name="utilizzatore" nillable="true" type="impl:ArrayOf_tns1_Utilizzatore"/>
      </sequence>
    </extension>
  </complexContent>
</complexType>

What I found I am not the only one experiencing this problem. In particular I found this comment in the PHP official documentation and this other forum entry to give two different ideas on how to approach the problem, but I have not been able to turn any of those two ideas into a working solution: I seem not to completely understand the logic behind the examples given.

I would be grateful if anybody could guide me in this: some working code on another webservice would be welcome, but what I am primarily after is really understanding the problem and the logic of the solutions proposed (the fish lane, not the fish!). :)

Thank you in advance for your time.

A: 

i have the same problem... u got any solution?

anusha
Unluckily not. At the end - since it's a custom service created by a third party for the busness we are developing for - we agreed with the service provider to modify the webservice according to PHP limitations. Very disappointed by this "bug" in PHP, though! :(
mac
Can WSO2- wsf/php be a solution for this issue?
anusha
A: 

Here are my immediate thoughts, sorry this isn't a proper answer, just some ideas...

First, have you tried viewing the soap request (the envelope) sent to the soap server? Does it look like it should work? Can you see where it is going wrong? Are you just getting an error back, a soapFault, or the wrong data, or nothing at all?

Second, have you tried using the SoapParam class?

Finally, I'm sure you're doing this right, but I notice that the object you are building has username and fieldOne and fieldTwo all side by side, but your WSDL shows that fieldOne and fieldTwo are part of the class Cliente (which never shows up in your example) while username should be inside of the utilizzatore array, so shouldn't it be more like:

stdClass Object
(
    [Cliente] => stdClass Object
        (
            [fieldOne] => ...
            [fieldTwo] => ...
            [utilizzatore] => stdClass Object
                ( // This is EMPTY instead of containing a series of userName's
                )

        )

)

The SoapClient class is very frustrating for me to, so don't take any of this as a criticism, because I only hope to better understand it myself by offering up ideas that might help you.

Anthony
@Anthony - No need to apologise for this not being "a proper answer"... I truly appreciate you took the time to look into this. As you might have read in my comment to anusha, we finally opted to modify the webservice rather than the client. However I still want to understand/resolve the issue, so the question is still open. :) As for the points you raised, see next comment.
mac
@Anthony - 1) SOAP WS works fine with java client, PHP throw no errors but does not populate the _utilizzatore_ object. I am under the impression that _utilizzatore_ is _NULL_ if the WS returns no data, while it is an _empty object_ if there is some data in the XML. 2) SoapParam: I tried very hastly (without success) after the decision of modifying the WS was already taken. I am happy to try it again with more calm if you think this is the way to go: do you have any pointer other than the very terse documentation on PHP.net? 3) My bad. I added the relevant bit in the WSDL part of my question.
mac
I'm just glad I've learned enough about WS and SOAP to have caught it! You didn't mention what the Soap Response and Requests actually are. I bet that would be a lot more revealing then what the variables are being set to. Use `__getLastRequest` and `__getLastResponse` to see the XML sent and received. Add Headers to the end of either to see the HTTP headers for either. The request will show you how the PHP variables are transmitted as XML. I bet you'll spot right away the problem, even if the solution still is mysterious.
Anthony
A: 

Mac, thanks a lot for your prompt responses. look at what i tumbled on.. I did not look at this earlier. Hence want to share this. http://bugs.php.net/search.php?cmd=display&amp;status=All&amp;search_for=extension+base&amp;php_os=&amp;php_os_not=0&amp;boolean=1&amp;author_email=&amp;bug_age=0&amp;by=&amp;order_by=php_version&amp;direction=DESC&amp;phpver=&amp;limit=10&amp;assign=&amp;bug_type[]=SOAP+related

anusha