我正在尝试使用nuSOAP访问WebService(因为我在这里绑定了PHP4),它在消息中使用了多个命名空间。这可能吗?
示例请求消息如下所示:
<soapenv:Envelope ...
xmlns:ns1="http://domain.tld/namespace1"
xmlns:ns2="http://domain.tld/namespace2">
<soapenv:Header/>
<soapenv:Body>
<ns1:myOperation>
<ns2:Person>
<ns2:Firstname>..</ns2:Firstname>
..
</ns2:Person>
<ns1:Attribute>..</ns1:Attribute>
</ns1:myOperation>
</soapenv:Body>
</soapenv:Envelope>
我试着跟随:
$client = new nusoap_client("my.wsdl", true);
$params = array(
'Person' => array(
'FirstName' => 'Thomas',
..
),
'Attribute' => 'foo'
);
$result = $client->call('myOperation', $params, '', 'soapAction');
希望nuSOAP尝试将这些名称与正确的名称空间和节点相匹配。然后我尝试使用soapval()来生成元素及其命名空间 - 但是如果我调用一个操作,nuSOAP会创建以下请求:
<SOAP-ENV:Envelope ...>
<SOAP-ENV:Body>
<queryCCApplicationDataRequest xmlns="http://domain.tld/namespace1"/>
</SOAP-ENV:Body>
</SOAP-ENV:Envelope>
在“匹配”阶段出现问题。
答案 0 :(得分:5)
在尝试匹配之后,我找到了两种可能的解决方案:
1)不要使用WSDL创建nusoap_client和soapval()来创建消息 这样做的缺点是消息包含大量开销(命名空间在每个元素中定义)。不太好。
2)不要依赖于参数的匹配,而是在xml中构建你的回复,并将前缀的所有定义放在第一个元素中 - 例如
$params = "<ns1:myOperation xmlns:ns1="..." xmlns:ns2="...">
<ns2:Person>
<ns2:Firstname>..</ns2:Firstname>
..
</ns2:Person>
<ns1:Attribute>..</ns1:Attribute>
</ns1:myOperation>";
仍然不是一个非常好的解决方案,但它的工作原理: - )
答案 1 :(得分:4)
在Irwin的帖子的基础上,我手动创建了xml,其余的则是nusoap。我的webhost没有php soap扩展,因此我不得不使用nusoap,而我正在尝试使用的Web服务需要每个标记上的命名空间(例如,在我的示例中使用用户名和密码)。
require_once('lib/nusoap.php');
$client = new nusoap_client('https://service.somesite.com/ClientService.asmx');
$client->soap_defencoding = 'utf-8';
$client->useHTTPPersistentConnection(); // Uses http 1.1 instead of 1.0
$soapaction = "https://service.somesite.com/GetFoods";
$request_xml = '<?xml version="1.0" encoding="utf-8" ?>
<env:Envelope xmlns:xsd="http://www.w3.org/2001/XMLSchema"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:env="http://schemas.xmlsoap.org/soap/envelope/">
<env:Body>
<n1:GetFoods xmlns:n1="https://service.somesite.com">
<n1:username>banjer</n1:username>
<n1:password>theleftorium</n1:password>
</n1:GetFoods>
</env:Body>
</env:Envelope>
';
$response = $client->send($request_xml, $soapaction, '');
echo '<h2>Request</h2><pre>' . htmlspecialchars($client->request, ENT_QUOTES) . '</pre>';
echo '<h2>Response</h2><pre>' . htmlspecialchars($client->response, ENT_QUOTES) . '</pre>';
echo '<h2>Debug</h2><pre>' . htmlspecialchars($client->getDebug(), ENT_QUOTES) . '</pre>';
然后我有一个错误说:
Notice: Undefined property: nusoap_client::$operation in ./lib/nusoap.php on line 7674
所以我走了懒惰路线进入nusoap.php并在第7674行之前添加了这段代码,以使它开心:
if(empty($this->operation)) {
$this->operation = "";
}
答案 2 :(得分:1)
另一个绕过这个问题的是对nusoap_client :: call()函数的修改。在nusoap.php中的这一行(版本1.123中的7359)旁边:
$nsPrefix = $this->wsdl->getPrefixFromNamespace($namespace);
我添加了这个:
$nsPrefix = $this->wsdl->getPrefixFromNamespace("other_ns_name");
它有效!由于我只为一个项目需要这个库,所以我可以硬编码这个hack。否则,我会挖掘更多并修改函数以接受数组而不是字符串参数的字符串。
答案 3 :(得分:0)
是的,我一直有同样的问题(通过谷歌找到你的q!)而且我遇到过这个问题: http://www.heidisoft.com/blog/using-nusoap-consume-net-web-service-10-min 这里,dev在coe中创建消息的xml主体,然后使用nusoap提交。