Ben*_*n D 7 php xsd soap soap-client
我的应用程序通常连接到第三方服务器以通过SOAP/WSDL获取数据:
$this->soap_client = new SoapClient("https://[the-domain]:443/[path]?wsdl", array(
'trace'=>1,
'login'=>$this->username,
'password'=>$this->password,
'exceptions' => true,
'cache_wsdl' => WSDL_CACHE_NONE
)
Run Code Online (Sandbox Code Playgroud)
去年一切都很好,但他们最近更新了他们的WSDL文件,现在当应用程序尝试连接时,我收到以下两个错误:
SoapClient::SoapClient(http://[the-domain]:80/[path]?xsd=1): failed to open stream: HTTP request failed! HTTP/1.1 401 Unauthorized
和
SoapClient::SoapClient(): I/O warning : failed to load external entity "http://[the-domain]:80/[path]?xsd=1"
当我查看WSDL XML文件时,看起来违规的可卸载文件是它试图导入的文档模式文件(schemaLocation):( 来自WSDL :)
<types>
<xsd:schema>
<xsd:import namespace="[irrelevant]" schemaLocation="http://[the-domain]:80/[path]?xsd=1"/>
</xsd:schema>
</types>
Run Code Online (Sandbox Code Playgroud)
我已经打了一会儿反对这一点,据我所知,问题是两件事之一:
302 redirects
到https
URL(并删除端口声明)时.尝试导入架构时,SOAP调用是否可能不遵循重定向?假设这是第二个问题,有没有办法可以强制系统使用不同的架构URL而无需下载WSDL文件,编辑它,并在本地存储/引用它?如果是这样,我可以尝试传递URL(http://username:password@domain....
)中的凭据?
如果我唯一的目的是创建WSDL和XSD模式文件的修改副本,那么就这样吧,但是我很想知道是否有人有任何想法可以让我避免这种情况(因为模式确实从时间变化 - 到时间).
看起来 PHP SoapClient 坚持使用相同的域策略(包括方案)来在 WSDL 请求中发送基本身份验证用户名和密码,这是为了在 WDSL 架构中导入 xsd 文件。
因此,如果 WSDL url 有一个https
方案并且导入有一个http
方案,PHP 不会发送基本身份验证信息,因为请求导入 url 时连接不再加密http
(这会损害身份验证信息的机密性)。
然而,似乎至少对于某些 PHP 版本(可能在较新版本中已修复),即使http
url 重定向到该版本https
(在同一域上),身份验证问题仍然存在。在重定向到具有相同域的安全 URL 之后,PHP 当然可以再次包含给定的基本身份验证信息。
最后,我发现解决此问题的唯一巧妙方法是让对方更改其 WSDL 内容以导入安全 URL(https
一个),该 URL 与 WDSL url 本身具有相同的方案、域和端口。
如果这不是您的选择,您当然可以随时寻求解决方法,即将 WSDL 以及导入保存为本地文件,并引用 WDSL 文件而不是URL。当然,这也意味着您必须更改 WSDL 以导入正确的本地文件(而不是 URL http
),并且可能还需要更改其他导入。不幸的是,这是我所知道的在这种情况下的唯一解决方法。
我还发现了这个可能相关的PHP 错误报告。