Zend Framework

Consultez la FAQ sur le ZF avant de poster une question

Vous n'êtes pas identifié.

#1 24-09-2011 13:44:59

JoeBoo
Nouveau membre
Date d'inscription: 24-09-2011
Messages: 1

spl_autoload_register avec namespace sans aucun require_once dans ZF

Bonjour,

J'ai découvert un truc génial que je veux partager avec la communauté.
Peut être que quelqu'un d'autre l'a trouvé avant moi, mais je n'ai rien trouvé la dessus.

J'ai trouvé un moyen d'utilser les namespaces de PHP 5.3 avec le ZF 1.11.6 (sans aucun require_once) par le biais de la classe
Opl\Autoloader\GenericLoader.

1 Suppression de require once du ZF
    J'utilise le code ci-dessous que j'appel via http://127.0.0.1/removeRequireOnce.php
    qui supprime les require_once de Zend, Zendx.
    Les fichiers modifiés vont dans les répertoires zZend, zZendX.

    Comme cela on peut vérifier et si on est satisfait on peut supprimer Zend, ZendX et
    renommer les répertoires zZend en Zend et zZendX en ZendX.
    Ci-dessous le contenu de mon fichier removeRequireOnce.php

Code:

[lang=php]
<?php
     
      function stripRequires($file) {
        $exception = array('/Loader/Autoloader.php','/Application.php');
        $content = file_get_contents($file);
        if( substr($file, -4) == '.php'
            && substr($file, -strlen($exception[0])) != $exception[0] 
            && substr($file, -strlen($exception[1])) != $exception[1] 
          ) {
         $content = preg_replace('#^\s*require_once.*;$#iUm', '// \1', $content, -1, $iCount);

         return $content;
        }
        return $content;
      }
     
      function removeRequireOnce($dir, $target) {
        if(!is_dir($target))
          mkdir($target);
     
        $myDirectory = opendir($dir);
        while($f = readdir($myDirectory)) {
          if($f != '.' && $f != '..'){
            if(is_dir($dir.$f)){
              removeRequireOnce($dir.$f.'/',$target.$f.'/');
            }else{
              $content = stripRequires($dir.$f);
              if($content !== FALSE)
                file_put_contents($target.$f, $content);
            }
          }
        }
        closedir($myDirectory);
      }

    removeRequireOnce('D:/DEV/SRC/www/MyProject/library/Zend/', 'D:/DEV/SRC/www/MyProject/library/zZend/');
    removeRequireOnce('D:/DEV/SRC/www/MyProject/library/ZendX/', 'D:/DEV/SRC/www/MyProject/library/zZendX/');

2 Mise en place de la librairie autoloader
    - Télécharger le fichier opl-autoloader-3.0.3.0.zip (Open Power Autoloader 3.0.3) sur ce site Opl
    - Mettre le répertoire Opl qui se trouve dans src/Opl dans le répertoire library.

Cette methode est aussi valable avec d'autres classes d'autoloading qui prennent en charge les séparateurs de namespaces '_', '\'

3 Mise en place de index.php

Ci-dessous le contenu de mon fichier index.php

   

Code:

[lang=php]<?php
    define('ROOT_PATH', realpath(dirname(__FILE__) . DIRECTORY_SEPARATOR . '..'));
    define('LIBRARY_PATH', ROOT_PATH . DIRECTORY_SEPARATOR . 'library');
    define('APPLICATION_PATH', ROOT_PATH . DIRECTORY_SEPARATOR . 'application');
    define('APPLICATION_ENV', 'production');
        
    // Ensure library/ is on include_path
    set_include_path(implode(PATH_SEPARATOR, array(
        LIBRARY_PATH,
        ROOT_PATH . '/models',
        '.'
    )));

    require_once LIBRARY_PATH . '/Zend/Loader/Autoloader/Interface.php';
    require_once LIBRARY_PATH . '/Zend/Loader/Autoloader.php';
    require(LIBRARY_PATH . '/Opl/Autoloader/GenericLoader.php');

    $oAutoLoader = Zend_Loader_Autoloader::getInstance();
    $oAutoLoader->unregisterNamespace(array('Zend_', 'ZendX_'));

    $oGenLoader = new Opl\Autoloader\GenericLoader(LIBRARY_PATH, '_');
    $oGenLoader->addNamespace('Zend');
    $oGenLoader->addNamespace('ZendX');
    $oGenLoader->register();
    //$oAutoLoader->pushAutoloader($oGenLoader, array('Zend', 'ZendX'));

    $oGenLoader = new Opl\Autoloader\GenericLoader(LIBRARY_PATH);
    $oGenLoader->addNamespace('ZL');
    $oGenLoader->addNamespace('ENV', APPLICATION_PATH . '/models');
    $oGenLoader->register();
    //$oAutoLoader->pushAutoloader($oGenLoader, array('ENV', 'ZL'));

    $oApplication = new Zend_Application(
        APPLICATION_ENV,
        APPLICATION_PATH . '/configs/application.ini'
    );

    $oApplication->bootstrap()
        ->run()
    ;

4 Ci-dessous un exemple d'utilisation dans un projet de test

C'est un exemple de code qui me sert à tester mon implémentation des NestedSetTree alors SVP ne me dite pas que le code n'est pas super.

Code:

[lang=php]<?php

use ENV\Domain\Nst\Node,
    ENV\Domain\Form\Node as NodeForm;

class IndexController extends Zend_Controller_Action {
    public function __construct(Zend_Controller_Request_Abstract $oRequest, Zend_Controller_Response_Abstract $oResponse, array $aInvokeArgs = array()) {
        parent::__construct($oRequest, $oResponse, $aInvokeArgs);
    }
    
    public function indexAction() {

        $oDbAdapter    = $this->getFrontController()->getParam('bootstrap')->getResource('database');
        
        $oDbAdapter->getConnection()->query("TRUNCATE TABLE `node`");
        $oDbAdapter->getConnection()->query("START TRANSACTION");
        
        $oTree = new Node();
        $oTree->buildTree();
        
        $oDbAdapter->getConnection()->query("COMMIT");
        
        $this->view->sTreeData = $oTree->dump();
        
        $aNodeList    = array(); 
        $oIt        = new \RecursiveIteratorIterator($oTree->getRoot()->getTree(), \RecursiveIteratorIterator::SELF_FIRST);
        foreach($oIt as $oNode) {
            $iLevel = $oIt->getDepth();
        
            /* @var $oNode \ENV\Nst\Node */
            $aNodeList[$oNode->getAt('sData')] = $oNode->getNodeId();
        }
        
        ksort($aNodeList);
        $this->view->aNodeList    = $aNodeList;
        $this->view->aOperation    = array(
            'moveTreeToFirstChild',
            'moveTreeToLastChild',
            'moveTreeToNextSibling',
            'moveTreeToPrevSibling',
            'moveToFirstChild',
            'moveToLastChild',
            'moveToPrevSibling',
            'moveToNextSibling'
        );
        
        $this->view->oForm = new NodeForm();
        
        $this->renderScript('index/index.phtml');
    }
    
    
    public function doOperationAction() {
        $iIdFrom    = (int) $this->_request->getParam('nodeFrom', 0);
        $iIdTo        = (int) $this->_request->getParam('nodeTo', 0);
        $sMethod    = (string) $this->_request->getParam('operation', '');
        $oFrom        = new Node();
        $oTo        = new Node();
        $oTree        = new Node();
        
        $this->indexAction();
        
        try {
            $oFrom->setNodeId($iIdFrom);
            $oFrom = $oTree->getNode($oFrom);
            
            $oTo->setNodeId($iIdTo);
            $oTo = $oTree->getNode($oTo);

            $oFrom->$sMethod($oTo);
            
            $this->view->sTreeData = $oTree->dump();
            
            $this->renderScript('index/do-operation.phtml');
        } catch(Exception $oEx) {
            echo $oEx->getMessage() . "<br />";
        }
    }
}

Un lien vers une image qui contient la structure de mon projet MonProject


Alors qu'en pensez-vous ?

Je me suis rendu compte que les deux lignes ci-dessous ne servent peut être à rien car lorsque je les mets en commentaire cela fonctionne aussi.
    $oAutoLoader->pushAutoloader($oGenLoader, array('Zend', 'ZendX'));
    $oAutoLoader->pushAutoloader($oGenLoader, array('ENV', 'ZL'));

Je suis certain que toutes les classes sont chargées par le biais de la classe Opl\Autoloader\GenericLoader car lorsque j'active le profilage et que je regarde le log avec kcachegring pour Windows je le constate.

Si quelqu'un a une info je suis preneur. En attendant je vais lire la documentation sur spl_autoload pour essayer de comprendre ce qui se passe exactement.

J'ai encore simplifié le code car je me suis rendu compte que la modification de la classe Opl\Autoloader\GenericLoader n'est pas nécessaire (trop de fougue, à force de faire des tests).

Dernière modification par JoeBoo (27-09-2011 19:31:52)

Hors ligne

 

#2 21-08-2012 09:56:34

skeniaskife
Nouveau membre
Lieu: Israel
Date d'inscription: 21-08-2012
Messages: 1
Site web

Re: spl_autoload_register avec namespace sans aucun require_once dans ZF

+1. c'est très intéressant

Hors ligne

 

Pied de page des forums

Propulsé par PunBB
© Copyright 2002–2005 Rickard Andersson
Traduction par punbb.fr

Graphisme réalisé par l'agence Rodolphe Eveilleau
Développement par Kitpages