<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>
I am trying to create a simple test web service in php using Zend Framework 2.2.1. I am using XAMPP v1.8.2-0. The version of php installed is 5.4.16. I have followed the skeleton application tutorial at http://framework.zend.com/manual/2.0/en/user-guide/skeleton-application.html up to the point where I have a functioning controller.
The wsdl path is testws.localhost/album/wsdl or testws.localhost/album?wsdl The service is located at testws.localhost/album. 127.0.0.1 in place of testws.localhost makes no difference.
Visiting the WSDL url returns me what appears to be a valid WSDL file, XMLSpy loads/validates it. Visiting the service in browser results in the error response above, which does not give any detail as to why it cannot load the WSDL.
Saving the generated WSDL output to file and using the path to that, as well as generating it as text in php within the soap request method all generate the same error, couldnt load from 'X' : failed to load external entity 'X'. The WSDL file can be read from where it is in the application directory and echoed out.
I have spent multiple days trying to resolve this and looked at plenty of similar questions here and on the web but all of them either magically resolve themselves or have no accepted answer, and nothing suggested worked for me. The code is included below, if there is any other information required let me know, I am relatively inexperienced with zend framework / php / xampp and this has me stopped completely.
AlbumController.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");
}
}
}
Soaptest.php
<?php
class Soaptest {
/**
* This method returns a string
*
* @param String $value
* @return String
*/
public function hello($value) {
return "hi";
}
}
in 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>
hosts file
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>
I think the problem is in your controller, first your $_URI
must be
$_URI = "http://testws.localhost/album";
(i.e. with the http schema).
second you are passing the wrong argument to AutoDiscover
, the first argument of the AutoDiscover
is not the url, try replacing your handleWSDL
method with this:
private function handleWSDL() {
$autodiscover = new AutoDiscover();
$autodiscover->setClass('Soaptest')
->setUri($this->_URI);
$autodiscover->handle();
}