Symfony – Create a Soap server with Zend Soap

In this example we will create an ApiBundle and a Soap server. Then a simple web service that return the name you send.

Install Zend Framework Vendor

To install Zend Framework vendor, execute

# composer require zendframework/zend-soap

Create ApiBundle

To create the ApiBundle, execute

# php app/console generate:bundle --namespace=Acme/ApiBundle --format=yml

Add routing in app/config/routing.yml

# app/config/routing.yml
acme_api:
    resource: "@AcmeApiBundle/Resources/config/routing.yml"
    prefix:   /api

Create the service

In Acme/ApiBundle/Services/ directory, Add CheckService.php

# Acme/ApiBundle/Services/CheckService.php
namespace Acme\ApiBundle\Services;
class CheckService
{
    /**
     * Check soap service, display name when called
     * @param string $name 
     * @return mixed
     */
    public function check($name)
    {
        return 'Hello '.$name;
    }
}

Add CheckService in Acme/ApiBundle/Ressources/services.yml

# Acme/ApiBundle/Ressources/services.yml
services:
     check_service:
         class: Acme\ApiBundle\Services\CheckService

Create the Soap Server

Create the soap controller

# Acme/ApiController/Controller/SoapController.php
namespace Acme\ApiBundle\Controller;
use Symfony\Bundle\FrameworkBundle\Controller\Controller;
use Symfony\Component\HttpFoundation\Response;
use Zend\Soap;
class SoapController extends Controller
{
    public function init()
    {
        // No cache
        ini_set('soap.wsdl_cache_enable', 0);
        ini_set('soap.wsdl_cache_ttl', 0);
    }

    public function checkAction()
    {
        if(isset($_GET['wsdl'])) {
            return $this->handleWSDL($this->generateUrl('acme_api_soap_check', array(), true), 'check_service'); 
        } else {
            return $this->handleSOAP($this->generateUrl('acme_api_soap_check', array(), true), 'check_service'); 
        }
 }

    /**
    * return the WSDL
    */
    public function handleWSDL($uri, $class)
    {
        // Soap auto discover
        $autodiscover = new Soap\AutoDiscover();
        $autodiscover->setClass($this->get($class));
        $autodiscover->setUri($uri);

       // Response
       $response = new Response();
       $response->headers->set('Content-Type', 'text/xml; charset=ISO-8859-1');
       ob_start();

       // Handle Soap
       $autodiscover->handle();
       $response->setContent(ob_get_clean());
       return $response;
    }

    /**
     * execute SOAP request
     */
    public function handleSOAP($uri, $class)
    {
        // Soap server
        $soap = new Soap\Server(null,
            array('location' => $uri,
            'uri' => $uri,
        ));
        $soap->setClass($this->get($class));

        // Response
        $response = new Response();
        $response->headers->set('Content-Type', 'text/xml; charset=ISO-8859-1');

        ob_start();
        // Handle Soap
        $soap->handle();
        $response->setContent(ob_get_clean());
        return $response;
    }
}

Create the route

# Acme/ApiBundle/Resources/config/routing.yml
acme_api_soap_check:
    path: /soap/check
    defaults: { _controller: AcmeApiBundle:Soap:check }

Soap client

You can display the wsdl with

http://yoururl/api/soap/check?wsdl

And you can test the web service

$client = new SoapClient("http://yoururl/api/soap?wsdl");
$response = $client->check('Chuck');
var_dump($response);

It should return “Hello Chuck”

Use Doctrine in the Service

To use doctrine in a service, add the following parameter :

services:
     check_service:
         class: Acme\ApiBundle\Services\CheckService
         parameters: [ @doctrine.orm.entity_manager]

Then, in your service

use Doctrine\ORM\EntityManager;

class CheckService
{ 
    protected $em;
    public function __construct(EntityManager $em)
    {
        $this->em = $em;
    }
}

Now you can use $this->em to get the entity manager, like:

$repository = $this->em->getRepository('AcmeAdminBundle:Post');

 

 

Raphaël has written 45 articles

16 thoughts on “Symfony – Create a Soap server with Zend Soap

  1. Claudio says:

    SOAP-ERROR: Parsing WSDL: Couldn’t load from ‘http://10.0.2.15/~desarrollo/siafca_web/web/app_dev.php/soap?wsdl’ : failed to load external entity “http://10.0.2.15/~desarrollo/siafca_web/web/app_dev.php/soap?wsdl”

    This is my client:
    public function holaAction (){
    $client = new SoapClient(“http://10.0.2.15/~desarrollo/siafca_web/web/app_dev.php/soap?wsdl”);
    $response = $client->check(‘Chuck’);
    var_dump($response);
    }

    ????

      1. Victor says:

        I have the same problem. When i put the http://uam.local/webservice/soap/security?wsdl in my browser shows the xml

        Valida si un usario está en el sistema y devuelve sus privilegios.

        But when i try in php, send Fatal error: SOAP-ERROR: Parsing WSDL: Couldn’t load from ‘http://uam.local/webservice/soap/security?wsdl’ : Input is not proper UTF-8, indicate encoding ! Bytes: 0xE1 0x20 0x65 0x6E in C:\www\domains\default\checksoap.php on line 3

  2. Ross says:

    Hello, I need some like:
    Pepe
    35
    In my service I have a array:
    array (size=2)
    ‘firstname’ => string ‘Pepe’
    ‘lastname’ => string ‘Pepe’
    How I can create the tag in the xml? and put the value in the tag?
    Thanks 🙂

  3. John says:

    Hello Raphaël,
    Thanks for you Great blog, Help me a log,
    I’ve created soap same like this given information.
    but i am not able to call function or not any function is showing on soap function list. if i’ve your email address then i can send you xml file attachment and my code too.
    Here i’m not able to to explain properly,

    1. Raphaël says:

      Hi,
      I’m not using SOAP or Symfony anymore, now I prefer REST and Laravel.
      It seems good that you got a SOAP function list, now I think you should call your function as a method. For example, with “check” method below :

      $client = new SoapClient(“http://yoururl/api/soap?wsdl”);
      $response = $client->check(‘Chuck’);
      var_dump($response);

Leave a Reply

Your email address will not be published. Required fields are marked *

You may use these HTML tags and attributes: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <s> <strike> <strong>