問題描述
我正在嘗試向soap請求添加一些屬性.PHP.net 上評分最高的評論 (http://php.net/manual/en/soapvar.soapvar.php) 和這里和這里 在 SO 上都說同樣的話:
I'm trying to add a few attributes to a soap request. Top rated comment on PHP.net (http://php.net/manual/en/soapvar.soapvar.php) and here and here on SO all say the same thing:
$param = array(
"_" => 'value',
'attrName' => 'attributeName'
);
$p = new SoapVar($param, SOAP_ENC_OBJECT);
應該返回
<param attrName="attributeName">value</param>
這會很棒,除非當我運行該代碼塊時,我得到了這個 XML:
Which would be great, except when I run that block of code, I get this XML:
<param>
<_>value</_>
<attrName>attributeName</attrName>
</param>
這顯然是錯誤的.我肯定不是世界上唯一有這個問題的人嗎?自 2011 年以來,關于那一點點功能的文檔是否發(fā)生了變化?
which is clearly wrong. Surely I'm not the only person in the world to have this problem? Did the documentation on that little bit of functionality change since 2011?
推薦答案
是的,您不是唯一遇到此問題的人 - 我看過無數(shù)帖子,人們聲稱使用 SOAP_ENC_OBJECT 傳遞給 SoapVar 的數(shù)組解決了這個問題而其他人在相同的帖子上聲稱不同.并且文檔并不清楚原因(除了我一年前在 php.net 評論部分的帖子).
Yes, you are not the only one who having this issue - I have seen countless number of posts where people claim that array passed to SoapVar with SOAP_ENC_OBJECT solves the issue while other people claim otherwise on the same posts. And documentation is not clear on the reasons (apart from my post year ago in comments section of php.net).
面對同樣的問題,我已經(jīng)閱讀了 PHP SOAP 擴展的源代碼.基本上你使用的語法是絕對正確的:
Facing the same issue I have read the sources of PHP SOAP extension. Basically the syntax you have used is absolutely correct:
$param = array(
"_" => 'value',
'attrName' => 'attributeName'
);
$p = new SoapVar($param, SOAP_ENC_OBJECT);
文檔沒有說明:這種語法可能會產(chǎn)生兩種不同的結果(事實上甚至更多:PHP SOAP 可以用八種不同的方式表達它).正如您可能看到的,上面的代碼是模棱兩可的:上面的代碼中是什么說attrName"是一個屬性而不是一個元素?沒有什么.上面的代碼只是沒有足夠的信息讓 SoapClient 決定attrName"是什么,所以它默認為一個元素".
What the documentation does not say: this syntax may produce two different results (and in fact even more: PHP SOAP may express it in eight different ways). And as you may see the code above is ambiguous: what in the code above says that 'attrName' is an attribute and not an element? Nothing. The code above just don't have sufficient amount of information for SoapClient to decide what 'attrName' is and so it defaults to "an element".
SoapClient 可以在兩種模式下運行:非 WSDL 和 WSDL.在前一種模式下,您永遠不會得到您想要的結果:SoapClient 依賴類型信息將數(shù)組元素轉(zhuǎn)換為屬性.由于非 WSDL 模式中不存在類型信息,因此 SoapClient 將提供的數(shù)組表示為一組元素 - 正是您得到的.在 WSDL 模式中存在類型信息,因此 SoapClient 知道元素和屬性名稱,并且可以將它們與數(shù)組索引進行匹配.所以如果你想要你的屬性,你必須讓你的 SoapClient 處于 WSDL 模式.
SoapClient may operate in two modes: non-WSDL and WSDL. In former mode you would never get the result you want: SoapClient relies on type information in order to turn array element into attribute. As type information is not present in non-WSDL mode SoapClient represents the provided array as set of elements - exactly what you got. In WSDL mode type information is present and therefore SoapClient knows elements and attributes names and may match them to array indexes. So you MUST have your SoapClient in WSDL mode if you want your attributes.
基本上為了實現(xiàn)你想要的,你需要在 <xsd:attribute name="attrName" type="xsd:string"/> 文檔/文字模式下的 WSDL 文件在 <xsd 的適當部分:架構> 塊.
Basically in order to achieve what you want you need to have WSDL file in document/literal mode with <xsd:attribute name="attrName" type="xsd:string"/> in appropriate section in <xsd:schema> block.
為什么有些人聲稱屬性數(shù)組使用成功而其他人說它不起作用"的原因僅在于他們的設置:有些人有 WSDL 文件要使用,有些人只是想執(zhí)行 new SoapClient(null,大批(...));(這當然沒有達到他們的期望)
The reason why some people claim success about array use for attributes and other people say "It does not work" lies solely in their setup: some people have WSDL files to consume, some people just trying to do new SoapClient(null, array(...)); (which of course fails their expectations)
這篇關于php SoapVar 未設置屬性的文章就介紹到這了,希望我們推薦的答案對大家有所幫助,也希望大家多多支持html5模板網(wǎng)!