0
<SOAP-ENV:Envelope xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/">
    <SOAP-ENV:Body>
        <SOAP-ENV:Fault>
            <faultcode>WSDL</faultcode>
            <faultstring>
            SOAP-ERROR: Parsing WSDL: Couldn't load from 'http://testws.localhost/album/wsdl' : failed to load external entity "http://testws.localhost/album/wsdl"
            </faultstring>
        </SOAP-ENV:Fault>
    </SOAP-ENV:Body>
</SOAP-ENV:Envelope>

我正在尝试使用 Zend Framework 2.2.1 在 php 中创建一个简单的测试 Web 服务。我正在使用 XAMPP v1.8.2-0。安装的php版本是5.4.16。我已经按照http://framework.zend.com/manual/2.0/en/user-guide/skeleton-application.html上的骨架应用程序教程进行操作,直到拥有一个正常工作的控制器为止。

wsdl 路径是 testws.localhost/album/wsdl 或 testws.localhost/album?wsdl 服务位于 testws.localhost/album。127.0.0.1 代替 testws.localhost 没有区别。

访问 WSDL url 返回给我的似乎是一个有效的 WSDL 文件,XMLSpy 加载/验证它。在浏览器中访问服务会导致上面的错误响应,它没有详细说明为什么它无法加载 WSDL。

将生成的 WSDL 输出保存到文件并使用该文件的路径,以及在 soap 请求方法中将其生成为 php 中的文本都生成相同的错误,无法从“X”加载:无法加载外部实体“X”。可以从应用程序目录中的位置读取 WSDL 文件并回显。

我花了好几天的时间试图解决这个问题,并在这里和网络上查看了许多类似的问题,但所有这些问题要么神奇地解决了自己,要么没有接受的答案,而且没有任何建议对我有用。代码包含在下面,如果需要任何其他信息,请告诉我,我对zend framework / php / xampp相对缺乏经验,这让我完全停止了。

专辑控制器.php

<?php
namespace Album\Controller;

require_once 'Soaptest.php';

use Zend\Mvc\Controller\AbstractActionController;
use Zend\View\Model\ViewModel;
use Zend\Soap\Server;
use Zend\Soap\AutoDiscover;

class AlbumController extends AbstractActionController
{
    private $_WSDL_URI = "http://testws.localhost/album/wsdl";
    private $_URI = "http://testws.localhost/album";

    public function indexAction()
    {    
        if(isset($_GET['wsdl'])) 
        {
            $this->handleWSDL();
        } 
        else 
        {
            $this->handleSOAP();
        }
        return $this->getResponse();
    }

    public function wsdlAction()
    {   
        $this->handleWSDL();
        return $this->getResponse();
    }

    private function handleWSDL() {
        $autodiscover = new AutoDiscover();
        $autodiscover->setUri('Soaptest');
        $autodiscover->setClass($this->_URI);
        $autodiscover->handle();
    }

    private function handleSOAP() {
        try 
        {
            $server = new Server($this->_WSDL_URI);
            $server->setClass('Soaptest');
            $server->handle();          
        } 
        catch (Exception $E) 
        {  
            $E->faultstring->dump("error.wsdl"); 
        }  
    }
}

肥皂测试.php

<?php
class Soaptest {
    /**
     * This method returns a string
     * 
     * @param String $value
     * @return String
     */
    public function hello($value) {
        return "hi";
    }
}

在 httpd-vhosts.conf

<VirtualHost testws.localhost:80>
    DocumentRoot "C:/xampp/htdocs/ws/ZendApp/public"
    ServerName testws.localhost
    ServerAlias www.testws.localhost
    SetEnv APPLICATION_ENV "development"
    <Directory "C:/xampp/htdocs/ws/ZendApp/public">
        DirectoryIndex index.php
        AllowOverride All
        Order allow,deny
        Allow from all
    </Directory>
</VirtualHost>

主机文件

127.0.0.1           testws.localhost localhost

wsdl xml

<definitions xmlns="http://schemas.xmlsoap.org/wsdl/" xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/" xmlns:tns="http://testws.localhost/album" xmlns:soap="http://schemas.xmlsoap.org/wsdl/soap/" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:soap-enc="http://schemas.xmlsoap.org/soap/encoding/" xmlns:soap12="http://schemas.xmlsoap.org/wsdl/soap12/" name="Soaptest" targetNamespace="http://testws.localhost/album">
    <types>
        <xsd:schema targetNamespace="http://testws.localhost/album"/>
    </types>
    <portType name="SoaptestPort">
        <operation name="hello">
            <documentation>This method returns a string</documentation>
            <input message="tns:helloIn"/>
            <output message="tns:helloOut"/>
        </operation>
    </portType>
    <binding name="SoaptestBinding" type="tns:SoaptestPort">
        <soap:binding style="rpc" transport="http://schemas.xmlsoap.org/soap/http"/>
        <operation name="hello">
            <soap:operation soapAction="http://testws.localhost/album#hello"/>
            <input>
                <soap:body use="encoded" encodingStyle="http://schemas.xmlsoap.org/soap/encoding/" namespace="http://testws.localhost/album"/>
            </input>
            <output>
                <soap:body use="encoded" encodingStyle="http://schemas.xmlsoap.org/soap/encoding/" namespace="http://testws.localhost/album"/>
            </output>
        </operation>
    </binding>
    <service name="SoaptestService">
        <port name="SoaptestPort" binding="tns:SoaptestBinding">
            <soap:address location="http://testws.localhost/album"/>
        </port>
    </service>
    <message name="helloIn">
        <part name="value" type="xsd:string"/>
    </message>
    <message name="helloOut">
        <part name="return" type="xsd:string"/>
    </message>
</definitions>
4

3 回答 3

1

我认为问题出在你的控制器上,首先你$_URI必须是

$_URI = "http://testws.localhost/album";

(即使用 http 模式)。

其次,您将错误的参数传递给AutoDiscover, 的第一个参数AutoDiscover不是 url,请尝试用以下方法替换您的handleWSDL方法:

private function handleWSDL() {
    $autodiscover = new AutoDiscover();
    $autodiscover->setClass('Soaptest')
                 ->setUri($this->_URI);
    $autodiscover->handle();
}
于 2013-07-12T07:36:58.757 回答
1

我在 Zend + Php 上收到此错误

SOAP-ERROR: Parsing WSDL: Couldn't load from 'http://wsdl...' : failed to load external entity "http://wsdl..."

我发现问题是由于服务器无法访问 URL 造成的。这很有趣,但它发生在托管 web 服务的服务器无法 curl/wget/读取它自己的 wsdl url 的情况下。

尝试 cURL 的 wsdl URL,看看你能不能拿回一些东西?

于 2013-11-18T11:00:43.493 回答
0

看起来实际上根本没有真正的问题。我正在创建的 ac# 示例应用程序和 XMLSpy 都能够读取 wsdl 文件并向服务发出请求。

我猜测产生的错误是由于我的网络浏览器没有发送soap请求,并且为了处理wsdl文件soap服务器尝试将请求中的信息与服务描述进行匹配。我本以为会因为缺少有效的soap 请求而返回错误,而不是关于完全有效且可用的wsdl 文件的错误。不确定此错误是由 zend soap 服务器还是它使用的底层 php soap 服务器创建的。

因此,如果其他人看到此错误,请确保您使用正确的 soap 客户端进行测试。

于 2013-07-14T04:50:58.753 回答