关于PHP的SoapClient和SoapServer,WSDL模式的问题。
我需要,让我们说,用其中的数据创建XML的某个部分的摘要。使用SoapClient很容易。我从类__doRequest()
重载SoapClient
方法,对某些元素进行哈希处理,并将其作为元素<Hash></Hash>
添加到<SOAP-ENV:Header/>
中。
然后我将生成的XML发送到调用parent::__doRequest()
的SOAPServer。
我需要对响应XML做同样的事情。在服务器方面,我遇到了困难。似乎服务器只能将数据作为嵌套数组或对象发送,并以某种方式插入到客户端的响应XML中。我尝试使用SoapServer
的响应发送XML,然后返回空XML。
我真的需要解析和修改服务器端的XML(制作哈希,数字签名等),但到目前为止,无论我在哪里搜索,我都无法找到答案。我真的非常感谢你的帮助。感谢。
答案 0 :(得分:0)
您必须获取XML字符串不带XML声明并使用SoapVar解析它。
有关详细信息,请参阅how-return-custom-xml-response-in-soapserver-response。
简而言之,就是这个
您可以根据输入构建DOMDocument以及需要将其添加到其中的任何其他内容。 XSLT
是解析和更改XML的好方法(有关如何在php中使用xslt的简单示例,请再次参见上面的链接)。
然后,从您要返回的DOMNode
中选择DOMDocument
,并将saveXML
与此节点一起用作参数。这会将所需的XML保存为字符串而不使用声明。没有参数的普通saveXML()
会将根节点保存为字符串,包括声明。
因此:
$nodes = $dom -> getElementsByTagName ('chooseTheElementYouWishToReturn');
$node = $nodes -> item(0);
$result = new SoapVar ($dom -> saveXML($node), XSD_ANYXML);
return ($result);
当你想要返回根元素时,这当然也有效:
$result = new SoapVar ($dom -> saveXML($dom -> documentElement), XSD_ANYXML);
return ($result);
<强> ADDITION 强>
我注意到你希望在SOAP标题中添加一些东西,而不是添加到正文中 这有点棘手,但可以实现 - 我希望下面的内容符合您的需求。
首先,添加标题详细信息只能在函数脚本中完成,然后函数必须将服务器变量声明为全局,以便引用声明的全局(函数外部),如下所示:
<?php
class mySOAPclass {
function xxx ($arg) {
global $server;
// your code for the header part
// example
$auth = array();
$auth['UserName'] = 'user';
$auth['Password'] = 'pw';
$header = new SoapVar ($auth, SOAP_ENC_OBJECT);
// end example
$header = new SoapHeader ('http://schemas.xmlsoap.org/soap/header/', 'credentials', $header, false);
$server -> addSoapHeader ($header);
// your code for the body part, assuming it results in a DOM $dom
$result = new SoapVar ($dom -> saveXML($dom -> documentElement), XSD_ANYXML);
return ($result);
}
ini_set( "soap.wsdl_cache_enabled", "0");
$server = new SoapServer ("yourOwn.wsdl");
$server -> setClass ('mySOAPclass');
$server -> setObject (new mySOAPclass());
$server -> handle();
?>
请注意,首先需要从数组中构造SoapVar
;如果直接将数组提供给标题,则会得到丑陋的item / key和item / value节点。
以上导致以下返回结构:
<SOAP-ENV:Envelope
xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/"
xmlns:ns1="http://schemas.xmlsoap.org/soap/header/">
<SOAP-ENV:Header>
<ns1:credentials>
<UserName>user</UserName>
<Password>pw</Password>
</ns1:credentials>
</SOAP-ENV:Header>
<SOAP-ENV:Body>
...
</SOAP-ENV:Body>
</SOAP-ENV:Envelope>