<?xml version="1.0" encoding="UTF-8"?>
<!-- EN-Revision: 24249 -->
<!-- Reviewed: no -->
<sect1 id="zend.soap.autodiscovery">
    <title>Auto découverte</title>

    <sect2 id="zend.soap.autodiscovery.introduction">
        <title>Introduction à l'auto découverte</title>

        <para>
            Les fonctionnalités <acronym>SOAP</acronym> de Zend Framework sont proposées afin de simplifier
            l'accès aux services Web de type <acronym>SOAP</acronym>.
        </para>

        <para>
            <acronym>SOAP</acronym> est un protocole d'échange de données indépendant d'un langage. Il peut donc
            être utilisé avec une autre technologie que <acronym>PHP</acronym>.
        </para>

        <para>
            Il y a trois configurations d'utilisation de <acronym>SOAP</acronym> avec Zend Framework
            :<orderedlist>
                    <listitem>
                        <simpara>SOAP serveur application <acronym>PHP</acronym> &lt;---&gt; <acronym>SOAP</acronym> client application
                        <acronym>PHP</acronym></simpara>
                    </listitem>

                    <listitem>
                        <simpara>SOAP serveur application non <acronym>PHP</acronym> &lt;---&gt; <acronym>SOAP</acronym> client
                        application <acronym>PHP</acronym></simpara>
                    </listitem>

                    <listitem>
                        <simpara>SOAP serveur application <acronym>PHP</acronym> &lt;---&gt; <acronym>SOAP</acronym> client application
                        non <acronym>PHP</acronym></simpara>
                    </listitem>
                </orderedlist>
            </para>

        <para>
            Il est indispensable de connaître les fonctionnalités qu'offre un serveur <acronym>SOAP</acronym>,
            afin de pouvoir communiquer avec lui. <ulink
            url="http://www.w3.org/TR/wsdl">WSDL</ulink> est alors utilisé pour décrire en détail
            l'API des services disponibles sur un serveur <acronym>SOAP</acronym>.
        </para>

        <para>
            Le langage WSDL est assez complexe (voyez <ulink
            url="http://www.w3.org/TR/wsdl">http://www.w3.org/TR/wsdl</ulink> pour les détails ). Il
            est donc difficile d'écrire une définition WSDL correcte, à la main.
        </para>

        <para>
            Un autre problème concerne la synchronisation des changements dans l'API avec des
            fichiers WSDL déjà existants.
        </para>

        <para>
            Ces 2 problèmes peuvent être résolus avec la génération automatique de WSDL, qui
            permet d'analyser une classe ou des fonctions, d'en extraire les paramètres
            d'entrée/sortie, et de générer un fichier WSDL correct et compréhensible par le serveur
            et les clients <acronym>SOAP</acronym>.
        </para>

        <para>
            Il y a deux façons d'utiliser Zend Framework pour une application serveur <acronym>SOAP</acronym>:
            <itemizedlist>
                    <listitem>
                        <para>Utiliser des classes.</para>
                    </listitem>

                    <listitem>
                        <para>Utiliser des fonctions.</para>
                    </listitem>
                </itemizedlist>
            </para>

        <para>
            Ces deux façons sont supportées par la fonctionnalité d'auto génération de Zend
            Framework.
        </para>

        <para>
            Zend_Soap_AutoDiscovery supporte aussi la correspondance des types <acronym>PHP</acronym> vers <ulink
            url="http://www.w3.org/TR/xmlschema-2/">les types XSD</ulink>.
        </para>

        <para>
            Voici un exemple d'utilisation de l'auto découverte. La fonction
            <methodname>handle()</methodname> génère le fichier WSDL et l'envoie au navigateur : <programlisting
            role="php"><![CDATA[
class My_SoapServer_Class {
...
}

$autodiscover = new Zend_Soap_AutoDiscover();
$autodiscover->setClass('My_SoapServer_Class');
$autodiscover->handle();
]]></programlisting></para>

        <para>
            Si vous avez besoin d'accéder au fichier WSDL généré soit pour le sauvegarder dans
            un fichier ou en tant que chaîne de caractères, vous pouvez utiliser les méthodes
            <methodname>dump($filename)</methodname> ou <methodname>toXml()</methodname> que la classe AutoDiscover
            fournit.
        </para>

        <note id="zend.soap.autodiscovery.introduction.noserver">
            <title>Zend_Soap_Autodiscover n'est pas un serveur SOAP</title>

            <para>
                Il est très important de noter, que la classe
                <classname>Zend_Soap_Autodiscover</classname> n'agit pas en tant que serveur <acronym>SOAP</acronym>
                elle-même. Elle génère seulement le WSDL et le fournit à ceux qui accèdent à l'URL
                qu'elle écoute.
            </para>

            <para>
                Par défaut l'URI de <acronym>SOAP</acronym> est <code>'http://' .$_SERVER['HTTP_HOST'] .
                $_SERVER['SCRIPT_NAME']</code>, mais ceci peut être changé avec la méthode
                <methodname>setUri()</methodname> ou le paramètre de constructeur de la classe
                <classname>Zend_Soap_AutoDiscover</classname>. L'URI doit correspondre à un
                <classname>Zend_Soap_Server</classname> qui écoute les requêtes.
            </para>

            <para>
                <programlisting language="php"><![CDATA[
if(isset($_GET['wsdl'])) {
    $autodiscover = new Zend_Soap_AutoDiscover();
    $autodiscover->setClass('HelloWorldService');
    $autodiscover->handle();
} else {
    // pointing to the current file here
    $soap = new Zend_Soap_Server("http://example.com/soap.php?wsdl");
    $soap->setClass('HelloWorldService');
    $soap->handle();
}
]]></programlisting></para>
            </note>
        </sect2>

        <sect2 id="zend.soap.autodiscovery.class">
            <title>Auto découverte de classe</title>

        <para>
            Si une classe est utilisée dans un serveur SOAP, alors celle-ci devrait aussi être
            fournie à <classname>Zend_Soap_AutoDiscovery</classname> afin d'en générer le fichier
            WSDL : <programlisting language="php"><![CDATA[
$autodiscover = new Zend_Soap_AutoDiscover();
$autodiscover->setClass('My_SoapServer_Class');
$autodiscover->handle();
]]></programlisting></para>

        <para>
            Les règles suivantes sont utilisées lors de la génération du fichier WSDL :
            <itemizedlist>
                    <listitem>
                        <para>Le fichier WSDL généré décrit un service Web de type RPC.</para>
                    </listitem>

                    <listitem>
                        <para>Le nom du service crée sera le nom de la classe utilisée.</para>
                    </listitem>

                    <listitem>
                    <para>
                        <code>'http://' .$_SERVER['HTTP_HOST'] .
                        $_SERVER['SCRIPT_NAME']</code> est utilisé comme <acronym>URI</acronym> où le fichier WSDL est
                        disponible par défaut mais ceci peut être surchargé avec la méthode
                        <methodname>setUri()</methodname>.
                    </para>

                    <para>
                        Cet <acronym>URI</acronym> est aussi utilisé comme un espace de nom cible pour tous les
                        noms du service (incluant les types complexes décrits
                        éventuellement).
                    </para>
                </listitem>

                <listitem>
                    <para>
                        Les méthodes de la classe sont jointes dans un <ulink
                        url="http://www.w3.org/TR/wsdl#_porttypes">Port Type</ulink>.
                    </para>

                    <para>
                        <code>$className . 'Port'</code> est utilisé comme nom de Port
                        Type.
                    </para>
                </listitem>

                <listitem>
                    <para>
                        Chaque méthode de la classe est enregistrée comme une
                        opération.
                    </para>
                </listitem>

                <listitem>
                    <para>
                        Chaque prototype de méthode génère des messages de requête/réponse
                        correspondants.
                    </para>

                    <para>
                        Une méthode peut avoir plusieurs prototypes si des paramètres sont
                        optionnels.
                    </para>
                </listitem>
                </itemizedlist>
            </para>

        <note>
            <title>Important !</title>

            <para>
                L'auto génération du fichier WSDL (avec auto découverte de la classe) utilise
                les blocs de documentation de <acronym>PHP</acronym> insérés par le développeur dans ses classes, afin
                de trouver les types retournés. De ce fait, pour les types scalaires, c'est le seul
                moyen de les déterminer de manière sûre, et concernant les types de retour des
                méthodes, c'est le seul moyen de les découvrir (PHP étant faiblement typé).
            </para>

            <para>
                Ceci signifie que documenter de manière correcte vos classes et méthodes n'est
                pas seulement une bonne pratique, c'est tout simplement essentiel pour partager vos
                classes en tant que services <acronym>SOAP</acronym> auto générés.
            </para>
        </note>
    </sect2>

    <sect2 id="zend.soap.autodiscovery.functions">
        <title>Auto découverte des fonctions</title>

        <para>
            Si des fonctions doivent être utilisées (partagées) via un serveur SOAP, alors
            elles doivent être passées à <classname>Zend_Soap_AutoDiscovery</classname> pour générer
            un fichier WSDL : <programlisting language="php"><![CDATA[
$autodiscover = new Zend_Soap_AutoDiscover();
$autodiscover->addFunction('function1');
$autodiscover->addFunction('function2');
$autodiscover->addFunction('function3');
...
$autodiscover->handle();
]]></programlisting></para>

        <para>
            Les règles suivantes sont utilisées lors de la génération du fichier WSDL :
            <itemizedlist>
                    <listitem>
                        <para>Le fichier WSDL généré décrit un service web de type RPC.</para>
                    </listitem>

                    <listitem>
                        <para>Le nom du service crée sera le nom du script analysé (utilisé).</para>
                    </listitem>

                    <listitem>
                    <para>
                        <code>'http://' .$_SERVER['HTTP_HOST'] .
                        $_SERVER['SCRIPT_NAME']</code> est utilisé comme <acronym>URI</acronym> pour rechercher le
                        fichier WSDL.
                    </para>

                    <para>
                        Cet <acronym>URI</acronym> est aussi utilisé comme un espace de nom cible pour tous les
                        noms du service (incluant les types complexes décrits
                        éventuellement).
                    </para>
                </listitem>

                <listitem>
                    <para>
                        Les fonctions sont encapsulées dans un <ulink
                        url="http://www.w3.org/TR/wsdl#_porttypes">Port Type</ulink>.
                    </para>

                    <para>
                        <code>$functionName . 'Port'</code> est utilisé comme nom de Port
                        Type.
                    </para>
                </listitem>

                <listitem>
                    <para>Chaque fonction est enregistrée comme opération possible.</para>
                </listitem>

                <listitem>
                    <para>
                        Chaque prototype de fonction génère des messages de requête/réponse
                        correspondants.
                    </para>

                    <para>
                        Une fonction peut avoir plusieurs prototypes si des paramètres sont
                        optionnels.
                    </para>
                </listitem>
                </itemizedlist>
            </para>

        <note>
            <title>Important!</title>

            <para>
                L'auto génération du fichier WSDL (avec auto découverte des fonctions) utilise
                les blocs de documentation de <acronym>PHP</acronym> insérés par le développeur dans ses fonctions,
                afin de trouver les types retournés. De ce fait, pour les types scalaires, c'est le
                seul moyen de les déterminer de manière sûre, et concernant les types de retour des
                méthodes, c'est le seul moyen de les découvrir (PHP étant faiblement typé).
            </para>

            <para>
                Ceci signifie que documenter de manière correcte vos fonctions n'est pas
                seulement une bonne pratique, c'est tout simplement essentiel pour partager vos
                fonctions en tant que services <acronym>SOAP</acronym> auto générés.
            </para>
        </note>
    </sect2>

    <sect2 id="zend.soap.autodiscovery.datatypes">
        <title>Types de donnée auto découverts</title>

        <para>
            Les types de données d'entrée/sortie sont convertis en types spéciaux pour le
            réseau, suivant ces règles : <itemizedlist>
                    <listitem>
                        <para>Chaînes strings &lt;-&gt; <code>xsd:string</code>.</para>
                    </listitem>

                    <listitem>
                        <para>Entiers <acronym>PHP</acronym> &lt;-&gt; <code>xsd:int</code>.</para>
                    </listitem>

                    <listitem>
                        <para>Flottants <acronym>PHP</acronym> (décimaux) &lt;-&gt; <code>xsd:float</code>.</para>
                    </listitem>

                    <listitem>
                        <para>Booléens <acronym>PHP</acronym> &lt;-&gt; <code>xsd:boolean</code>.</para>
                    </listitem>

                    <listitem>
                        <para>Tableaux <acronym>PHP</acronym> &lt;-&gt; <code>soap-enc:Array</code>.</para>
                    </listitem>

                    <listitem>
                        <para>Objets <acronym>PHP</acronym> &lt;-&gt; <code>xsd:struct</code>.</para>
                    </listitem>

                    <listitem>
                    <para>
                        Classe <acronym>PHP</acronym> &lt;-&gt; basé sur la stratégie des types complexes (Voir :
                        <link linkend="zend.soap.wsdl.types.add_complex">cette section</link>) <footnote>
                            <para>
                                <classname>Zend_Soap_AutoDiscover</classname> sera créé avec
                                la classe
                                <classname>Zend_Soap_Wsdl_Strategy_DefaultComplexType</classname> en
                                tant qu'algorithme de détection pour les types complexes. Le premier
                                paramètre du constructeur AutoDiscover accepte toute stratégie de
                                types complexes implémentant
                                <classname>Zend_Soap_Wsdl_Strategy_Interface</classname> ou une
                                chaîne correspondant au nom de la classe. Pour une compatibilité
                                ascendante, avec <varname>$extractComplexType</varname> les variables
                                booléennes sont analysées comme avec Zend_Soap_Wsdl. Regardez le
                                manuel <link
                                linkend="zend.soap.wsdl.types.add_complex">Zend_Soap_Wsdl sur
                                l'ajout des types complexes</link> pour plus d'informations.
                            </para>
                            </footnote>.
                        </para>
                </listitem>

                <listitem>
                    <para>
                        <code>type[]</code> or <code>object[]</code> (c'est-à-dire
                        <code>int[]</code>) &lt;-&gt; basé sur la stratégie des types
                        complexes
                    </para>
                </listitem>

                <listitem>
                    <para>Void <acronym>PHP</acronym> &lt;-&gt; type vide.</para>
                </listitem>

                <listitem>
                    <para>
                        Si le type n'est pas reconnu en tant que l'un de ceux-ci, alors
                        <code>xsd:anyType</code> est utilisé.
                    </para>
                </listitem>
            </itemizedlist> Où <code>xsd:</code> est l'espace
        "http://www.w3.org/2001/XMLSchema", <code>soap-enc:</code> est l'espace
        "http://schemas.xmlsoap.org/soap/encoding/", <code>tns:</code> est "l'espace de nom
            cible" du service.
        </para>
    </sect2>

    <sect2 id="zend.soap.autodiscovery.wsdlstyles">
        <title>Styles de liaisons WSDL</title>

        <para>
            WSDL offre différents mécanismes et styles de transport. Ceci affecte les balises
            <code>soap:binding</code> et <code>soap:body</code> à l'intérieur de la section binding
            du WSDL. Différents clients ont différentes conditions quant aux options qui sont
            vraiment utilisées. Par conséquent vous pouvez placer les styles avant d'appeler
            n'importe quelle méthode <code>setClass</code> ou <code>addFunction</code> de la classe
            <code>AutoDiscover</code>.
        </para>

        <para>
            <programlisting language="php"><![CDATA[
$autodiscover = new Zend_Soap_AutoDiscover();
// Par défaut il s'agit de 'use' => 'encoded'
// et 'encodingStyle' => 'http://schemas.xmlsoap.org/soap/encoding/'
$autodiscover->setOperationBodyStyle(array('use' => 'literal', 'namespace' => 'http://framework.zend.com'));

// Par défaut il s'agit de 'style' => 'rpc'
// et 'transport' => 'http://schemas.xmlsoap.org/soap/http'
$autodiscover->setBindingStyle(array('style' => 'document', 'transport' => 'http://framework.zend.com'));
...
$autodiscover->addFunction('myfunc1');
$autodiscover->handle();
]]></programlisting>
            </para>
    </sect2>
</sect1>