Zend FR

Consultez la FAQ sur le ZF avant de poster une question

Vous n'êtes pas identifié.

#1 25-03-2012 01:52:17

inzaghi
Membre
Date d'inscription: 09-08-2011
Messages: 74

Comment créer des ACL dynamique ?

Salut ,
Je voudrais créer des profils dynamique selon le besoin d'un utilisateur .Ainsi , le menu apparait selon les privilèges accordés . Comment faire ?

Hors ligne

 

#2 25-03-2012 19:48:22

shadypierre
Membre
Date d'inscription: 24-03-2010
Messages: 617

Re: Comment créer des ACL dynamique ?

Ta question est assez large hmm
Pour faire court tu aura besoin de Zend_Acl et Zend_Auth

Hors ligne

 

#3 26-03-2012 16:22:57

inzaghi
Membre
Date d'inscription: 09-08-2011
Messages: 74

Re: Comment créer des ACL dynamique ?

shadypierre a écrit:

Ta question est assez large hmm
Pour faire court tu aura besoin de Zend_Acl et Zend_Auth

ça je le sais bien . JE t'explique mieux : J'ai un admin qui a tout les droit et qui peux attribuer un privilège qu'il choisi pour un autre "Role" visiteur par exemple . Comment peut il le faire d'une façon dynamique .

Hors ligne

 

#4 26-03-2012 21:18:57

Bouchra
Membre
Lieu: Montréal
Date d'inscription: 07-12-2011
Messages: 47

Re: Comment créer des ACL dynamique ?

Bonjour, j'ai le même souci. Je pense qu'il faut  un étude de cas pour bien comprendre comment attribuer les privilèges et les rôles à un utilisateur pour une  ressources données.

Je propose un exemple de la gestion des news bien vous avez le choix de proposer un autre thème.

Admin (publie l'article - supprime l'article);
Journaliste (ajoute un article - modifie l'article ) ;
Invité (lire l'article - ajoute un commentaire).

Donc la ressource est la gestion des articles, les rôles définit : Admin - Journaliste - Invité

Que pensez vous.

Hors ligne

 

#5 26-03-2012 23:05:50

inzaghi
Membre
Date d'inscription: 09-08-2011
Messages: 74

Re: Comment créer des ACL dynamique ?

Bouchra a écrit:

Bonjour, j'ai le même souci. Je pense qu'il faut  un étude de cas pour bien comprendre comment attribuer les privilèges et les rôles à un utilisateur pour une  ressources données.

Je propose un exemple de la gestion des news bien vous avez le choix de proposer un autre thème.

Admin (publie l'article - supprime l'article);
Journaliste (ajoute un article - modifie l'article ) ;
Invité (lire l'article - ajoute un commentaire).

Donc la ressource est la gestion des articles, les rôles définit : Admin - Journaliste - Invité

Que pensez vous.

Dans ton exemple tu met tes profil dès le début mais pour mon cas l'admin peut créer un autre profil qui a d'autres privilège c'est pour cela que j'ai dit que c'est dynamique .

Hors ligne

 

#6 27-03-2012 00:49:26

Bouchra
Membre
Lieu: Montréal
Date d'inscription: 07-12-2011
Messages: 47

Re: Comment créer des ACL dynamique ?

La réponse je pense est dans votre question dynamique. Ma proposition est de mettre en place une base de données. si un administrateur crée un nouvel utilisateur il doit lui attribuer un rôle sinon on attribut par défaut à cet utilisateur comme "Invité".  cad dans la table user il faut une colonne dite role et selon le rôle de cette nouvel utilisateur se dirigera vers la ressource attribuée.

Je vous donne juste une idée de conception et c'est à vous de voir surtout on parle d'un cas abstrait.

Mais pour moi le problème c'est comment mettre en application Zend_ACL. Je me suis bien documentée mais je me trouve bloquer pour pratiquer. A titre d'infos je m'autoformes en Zend et en POO, donc je suis débutante.smile

A vous.

Dernière modification par Bouchra (27-03-2012 00:54:28)

Hors ligne

 

#7 27-03-2012 03:26:58

inzaghi
Membre
Date d'inscription: 09-08-2011
Messages: 74

Re: Comment créer des ACL dynamique ?

Passons au pratique j'ai fait le LibraryAcl au dessus du model

Code:

<?php


class Model_LibraryAcl extends Zend_Acl {

    public function __construct() {
        $this->addResource(new Zend_Acl_Resource('index'));
        $this->addResource(new Zend_Acl_Resource('books'));
        $this->addResource(new Zend_Acl_Resource('liste'), 'books');
        $this->addResource(new Zend_Acl_Resource('book'));
        $this->addResource(new Zend_Acl_Resource('edit'), 'book');
        $this->addResource(new Zend_Acl_Resource('add'), 'book');
        $this->addResource(new Zend_Acl_Resource('delete'), 'book');
        $this->addRole(new Zend_Acl_Role('user'));
        $this->addRole(new Zend_Acl_Role('admin'), 'user');
        $this->allow('user', 'index');
        $this->allow('user', 'books', 'liste');
        $this->allow('admin', 'book', 'edit');
        $this->allow('admin', 'book', 'add');
        $this->allow('admin', 'book', 'delete');
        //$this->isAllowed('admin', 'error', 'error');


        }

}

Comment passer les privilèges de user selon les choix du l'admin ? Le deuxième problème c'est de cacher les lien d'edit par exemple pour le user

Hors ligne

 

#8 27-03-2012 13:35:15

tdutrion
Administrateur
Lieu: Dijon, Paris, Edinburgh
Date d'inscription: 23-12-2009
Messages: 614
Site web

Re: Comment créer des ACL dynamique ?

Pourquoi ne pas stocker tes rôles dans la base de données ou dans un fichier ?

Moi en général je procède comme ça, avec des tables acl_role, acl_resource, acl_role_inheritance...

Hors ligne

 

#9 27-03-2012 14:33:19

inzaghi
Membre
Date d'inscription: 09-08-2011
Messages: 74

Re: Comment créer des ACL dynamique ?

Théocrite a écrit:

Pourquoi ne pas stocker tes rôles dans la base de données ou dans un fichier ?

Moi en général je procède comme ça, avec des tables acl_role, acl_resource, acl_role_inheritance...

si tu as un code exemple ça m'aidera bcp .

Hors ligne

 

#10 27-03-2012 14:48:17

tdutrion
Administrateur
Lieu: Dijon, Paris, Edinburgh
Date d'inscription: 23-12-2009
Messages: 614
Site web

Re: Comment créer des ACL dynamique ?

Bon alors faut vraiment l'adapter, et au passage ça permettra aux autres de commenter mon code pour dire ce qu'ils en pensent...

Mon fichier App_Model_Acl est l'équivalent de ton Model_LibraryAcl. Il fait appel à d'autres classes que je décrirais ci-dessous.

Code:

[lang=php]
<?php
class App_Model_Acl extends Zend_Acl
{
    private $_roles;
    private $_rolesArray = array();
    private $_roleInheritance;
    private $_modules = array();

    public function __construct()
    {
        $this->_roles = new Application_Model_DbTable_Roles();
        $this->_roleInheritance = new App_Model_DbTable_RoleInheritance();
        $frontController = Zend_Controller_Front::getInstance();
        $this->_modules = array_keys($frontController->getControllerDirectory());

        $this->_initRessources();
        $this->_initRoles();
        $this->_initRights();

        Zend_Registry::set('Acl', $this);
    }

    protected function _initRessources()
    {
        $frontController = Zend_Controller_Front::getInstance();
        foreach($frontController->getControllerDirectory() as $module => $controllerPath) {
            foreach(glob($controllerPath.'/*Controller.php') as $controller) {
                $this->addResource(new Zend_Acl_Resource($module.'_'.strtolower(basename($controller,'Controller.php'))));
            }
        }
    }

    protected function _initRoles()
    {
        /* get roles from db */
        foreach ($this->_roles->fetchAll() as $role) {
            $this->_rolesArray[$role->idroles] = $role;
        }
        foreach ($this->_roles->fetchAll() as $role) {
            if(!$this->hasRole($role->idroles)) $this->setNewRole($role);
        }
    }

    protected function setNewRole($role) {
        $inheritance = $this->_roleInheritance->fetchAll('roleId="'.$role->idroles.'"');
        if(count($inheritance) > 0) {
            foreach ($inheritance as $i) {
                if(!$this->hasRole($i->parentRoleId)) $this->setNewRole($this->_rolesArray[$i->parentRoleId]);
                $this->addRole(new Zend_Acl_Role($role->idroles),$this->_rolesArray[$i->parentRoleId]->idroles);
            }
        } else {
            $this->addRole(new Zend_Acl_Role($role->idroles));
        }
    }


    protected function _initRights()
    {
        $this->allow(null,"default_error");
        $acl = new App_Model_DbTable_RoleAcl();
        foreach ($acl->fetchAll() as $value) {
            try {
                if($this->has($value->resource)):
                    if($value->permission == 'allow') $this->allow($value->idrole,$value->resource,!empty($value->actions)?explode(", ",$value->actions):null);
                    else $this->allow($value->idrole,$value->resource,!empty($value->actions)?explode(", ",$value->actions):null);
                elseif($value->resource == '*'):
                    if($value->permission == 'allow') $this->allow($value->idrole,NULL);
                    else $this->allow($value->idrole,NULL);
                elseif(in_array($value->resource, $this->_modules)):
                    $frontController = Zend_Controller_Front::getInstance();
                    $dir = $frontController->getControllerDirectory();
                    foreach(glob($dir[$value->resource].'/*Controller.php') as $controller) {
                        $this->allow($value->idrole,$value->resource.'_'.strtolower(basename($controller,'Controller.php')));
                    }
                endif;
                $auth = Zend_Auth::getInstance()->setStorage(new Zend_Auth_Storage_Session('auth'));
                if($auth->hasIdentity()) {
                    $this->allow($auth->getIdentity()->idroles,'client_index','logout');
                    $this->allow($auth->getIdentity()->idroles,'membre_index','logout');
                }
            } catch (Exception $e) { /** @todo log errors and display them in admin */ }
        }
    }

    public function isAllowed($role = null, $resource = null, $privilege = null) {
        if($this->hasRole($role) and $this->has($resource)) {
            return parent::isAllowed($role, $resource, $privilege);
        }
        $frontController = Zend_Controller_Front::getInstance();
        $modules = $frontController->getControllerDirectory();
        if(isset($modules[$resource])) {
            foreach(glob($modules[$resource].'/*Controller.php') as $controller) {
                if($this->has($resource.'_'.strtolower(basename($controller,'Controller.php'))) and !parent::isAllowed($role,$resource.'_'.strtolower(basename($controller,'Controller.php')))) return false;
            }
            return true;
        }
        return false;
    }
}

Tu remarqueras dans _initRessources que je fais un parcours de tous mes controllers, et je récupères toutes les actions.

J'ai aussi un plugin d'acl :

Code:

[lang=php]
<?php
class App_Plugins_Acl extends Zend_Controller_Plugin_Abstract
{

    private $_noauth = array(
        'module' => 'client',
        'controller' => 'index',
        'action' => 'login'
    );

    private $_noacl = array(
        'module' => 'default',
        'controller' => 'error',
        'action' => 'deny'
    );

    public function preDispatch(Zend_Controller_Request_Abstract $request)
    {
        $acl = null;
        $role = null;
        if(Zend_Registry::isRegistered('Acl')) {
            $acl = Zend_Registry::get('Acl');
        } else {
            throw new Zend_Controller_Exception("Acl not defined !");
        }
        $auth = Zend_Auth::getInstance()->setStorage(new Zend_Auth_Storage_Session('auth'));
        if($auth->hasIdentity()) {
            $user = $auth->getIdentity() ;
            $role = $user->idroles;
        } else {
            $role = 5;
        }
        $module = strtolower($request->getModuleName());
        $controller = strtolower($request->getControllerName());
        $action = strtolower($request->getActionName());
        $ressource = $acl->has($module.'_'.$controller)?$module.'_'.$controller:($acl->has($controller)?$controller:null);
        
    if(!$acl->isAllowed($role, $ressource, $action)) {
            if(!$auth->hasIdentity()) {
                $module = $this->_noauth['module'];
                $controller = $this->_noauth['controller'];
                $action = $this->_noauth['action'];
            } else {
                $module = $this->_noacl['module'];
                $controller = $this->_noacl['controller'];
                $action = $this->_noacl['action'];
            }
        }

        $request->setModuleName($module);
        $request->setControllerName($controller);
        $request->setActionName($action);
    }
}

Tu remarqueras le 5 codé en dur alors que ça correspond à une valeur par défaut de ma base de données... Pas cool...

Pour les autres classes, ce sont des classes DbTables toutes simples.

Hors ligne

 

#11 27-03-2012 14:57:11

inzaghi
Membre
Date d'inscription: 09-08-2011
Messages: 74

Re: Comment créer des ACL dynamique ?

Théocrite a écrit:

Bon alors faut vraiment l'adapter, et au passage ça permettra aux autres de commenter mon code pour dire ce qu'ils en pensent...

Mon fichier App_Model_Acl est l'équivalent de ton Model_LibraryAcl. Il fait appel à d'autres classes que je décrirais ci-dessous.

Code:

[lang=php]
<?php
class App_Model_Acl extends Zend_Acl
{
    private $_roles;
    private $_rolesArray = array();
    private $_roleInheritance;
    private $_modules = array();

    public function __construct()
    {
        $this->_roles = new Application_Model_DbTable_Roles();
        $this->_roleInheritance = new App_Model_DbTable_RoleInheritance();
        $frontController = Zend_Controller_Front::getInstance();
        $this->_modules = array_keys($frontController->getControllerDirectory());

        $this->_initRessources();
        $this->_initRoles();
        $this->_initRights();

        Zend_Registry::set('Acl', $this);
    }

    protected function _initRessources()
    {
        $frontController = Zend_Controller_Front::getInstance();
        foreach($frontController->getControllerDirectory() as $module => $controllerPath) {
            foreach(glob($controllerPath.'/*Controller.php') as $controller) {
                $this->addResource(new Zend_Acl_Resource($module.'_'.strtolower(basename($controller,'Controller.php'))));
            }
        }
    }

    protected function _initRoles()
    {
        /* get roles from db */
        foreach ($this->_roles->fetchAll() as $role) {
            $this->_rolesArray[$role->idroles] = $role;
        }
        foreach ($this->_roles->fetchAll() as $role) {
            if(!$this->hasRole($role->idroles)) $this->setNewRole($role);
        }
    }

    protected function setNewRole($role) {
        $inheritance = $this->_roleInheritance->fetchAll('roleId="'.$role->idroles.'"');
        if(count($inheritance) > 0) {
            foreach ($inheritance as $i) {
                if(!$this->hasRole($i->parentRoleId)) $this->setNewRole($this->_rolesArray[$i->parentRoleId]);
                $this->addRole(new Zend_Acl_Role($role->idroles),$this->_rolesArray[$i->parentRoleId]->idroles);
            }
        } else {
            $this->addRole(new Zend_Acl_Role($role->idroles));
        }
    }


    protected function _initRights()
    {
        $this->allow(null,"default_error");
        $acl = new App_Model_DbTable_RoleAcl();
        foreach ($acl->fetchAll() as $value) {
            try {
                if($this->has($value->resource)):
                    if($value->permission == 'allow') $this->allow($value->idrole,$value->resource,!empty($value->actions)?explode(", ",$value->actions):null);
                    else $this->allow($value->idrole,$value->resource,!empty($value->actions)?explode(", ",$value->actions):null);
                elseif($value->resource == '*'):
                    if($value->permission == 'allow') $this->allow($value->idrole,NULL);
                    else $this->allow($value->idrole,NULL);
                elseif(in_array($value->resource, $this->_modules)):
                    $frontController = Zend_Controller_Front::getInstance();
                    $dir = $frontController->getControllerDirectory();
                    foreach(glob($dir[$value->resource].'/*Controller.php') as $controller) {
                        $this->allow($value->idrole,$value->resource.'_'.strtolower(basename($controller,'Controller.php')));
                    }
                endif;
                $auth = Zend_Auth::getInstance()->setStorage(new Zend_Auth_Storage_Session('auth'));
                if($auth->hasIdentity()) {
                    $this->allow($auth->getIdentity()->idroles,'client_index','logout');
                    $this->allow($auth->getIdentity()->idroles,'membre_index','logout');
                }
            } catch (Exception $e) { /** @todo log errors and display them in admin */ }
        }
    }

    public function isAllowed($role = null, $resource = null, $privilege = null) {
        if($this->hasRole($role) and $this->has($resource)) {
            return parent::isAllowed($role, $resource, $privilege);
        }
        $frontController = Zend_Controller_Front::getInstance();
        $modules = $frontController->getControllerDirectory();
        if(isset($modules[$resource])) {
            foreach(glob($modules[$resource].'/*Controller.php') as $controller) {
                if($this->has($resource.'_'.strtolower(basename($controller,'Controller.php'))) and !parent::isAllowed($role,$resource.'_'.strtolower(basename($controller,'Controller.php')))) return false;
            }
            return true;
        }
        return false;
    }
}

Tu remarqueras dans _initRessources que je fais un parcours de tous mes controllers, et je récupères toutes les actions.

J'ai aussi un plugin d'acl :

Code:

[lang=php]
<?php
class App_Plugins_Acl extends Zend_Controller_Plugin_Abstract
{

    private $_noauth = array(
        'module' => 'client',
        'controller' => 'index',
        'action' => 'login'
    );

    private $_noacl = array(
        'module' => 'default',
        'controller' => 'error',
        'action' => 'deny'
    );

    public function preDispatch(Zend_Controller_Request_Abstract $request)
    {
        $acl = null;
        $role = null;
        if(Zend_Registry::isRegistered('Acl')) {
            $acl = Zend_Registry::get('Acl');
        } else {
            throw new Zend_Controller_Exception("Acl not defined !");
        }
        $auth = Zend_Auth::getInstance()->setStorage(new Zend_Auth_Storage_Session('auth'));
        if($auth->hasIdentity()) {
            $user = $auth->getIdentity() ;
            $role = $user->idroles;
        } else {
            $role = 5;
        }
        $module = strtolower($request->getModuleName());
        $controller = strtolower($request->getControllerName());
        $action = strtolower($request->getActionName());
        $ressource = $acl->has($module.'_'.$controller)?$module.'_'.$controller:($acl->has($controller)?$controller:null);
        
    if(!$acl->isAllowed($role, $ressource, $action)) {
            if(!$auth->hasIdentity()) {
                $module = $this->_noauth['module'];
                $controller = $this->_noauth['controller'];
                $action = $this->_noauth['action'];
            } else {
                $module = $this->_noacl['module'];
                $controller = $this->_noacl['controller'];
                $action = $this->_noacl['action'];
            }
        }

        $request->setModuleName($module);
        $request->setControllerName($controller);
        $request->setActionName($action);
    }
}

Tu remarqueras le 5 codé en dur alors que ça correspond à une valeur par défaut de ma base de données... Pas cool...

Pour les autres classes, ce sont des classes DbTables toutes simples.

la base de données des ACL est formée comment ? Puisse je créer d'autre privilège selon des choix case à cocher ou autre comme ça ?

Hors ligne

 

#12 27-03-2012 15:12:15

tdutrion
Administrateur
Lieu: Dijon, Paris, Edinburgh
Date d'inscription: 23-12-2009
Messages: 614
Site web

Re: Comment créer des ACL dynamique ?

Code:

[lang=sql]
CREATE TABLE IF NOT EXISTS `roles` (
  `idroles` int(11) NOT NULL AUTO_INCREMENT,
  `name` varchar(50) NOT NULL,
  PRIMARY KEY (`idroles`),
  UNIQUE KEY `name` (`name`)
) ENGINE=InnoDB  DEFAULT CHARSET=utf8 AUTO_INCREMENT=6 ;

INSERT INTO `roles` (`idroles`, `name`) VALUES
(1, 'Administrateur'),
(5, 'Autre'),
(2, 'Client'),
(4, 'Externe'),
(3, 'Prospect');

-- --------------------------------------------------------

CREATE TABLE IF NOT EXISTS `role_acl` (
  `idrole` int(11) NOT NULL,
  `resource` varchar(100) NOT NULL,
  `actions` varchar(5000) NOT NULL,
  `permission` enum('allow','deny') NOT NULL,
  PRIMARY KEY (`idrole`,`resource`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;

INSERT INTO `role_acl` (`idrole`, `resource`, `actions`, `permission`) VALUES
(1, '*', '', 'allow'),
(1, 'core', '', 'allow'),
(2, 'users_auth', 'login, register', 'deny'),
(5, 'default', '', 'allow'),
(5, 'gp', '', 'allow'),
(5, 'member_index', 'register, login', 'allow');

-- --------------------------------------------------------

CREATE TABLE IF NOT EXISTS `role_inheritance` (
  `roleId` int(11) NOT NULL,
  `parentRoleId` int(11) NOT NULL,
  PRIMARY KEY (`roleId`,`parentRoleId`),
  UNIQUE KEY `single_inheritance` (`roleId`),
  KEY `fk_role_inheritance_roles_child` (`roleId`),
  KEY `fk_role_inheritance_roles_parent` (`parentRoleId`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_unicode_ci;

INSERT INTO `role_inheritance` (`roleId`, `parentRoleId`) VALUES
(1, 5),
(2, 3),
(3, 5),
(4, 5);

-- --------------------------------------------------------

CREATE TABLE IF NOT EXISTS `users` (
  `idusers` int(11) NOT NULL AUTO_INCREMENT,
  `firstname` varchar(45) NOT NULL,
  `lastname` varchar(45) NOT NULL,
  `email` varchar(255) NOT NULL,
  `nickname` varchar(45) NOT NULL,
  `password` varchar(45) NOT NULL,
  `idroles` int(11) NOT NULL DEFAULT '5',
  PRIMARY KEY (`idusers`),
  UNIQUE KEY `UNIQUE` (`nickname`),
  KEY `roles` (`idroles`)
) ENGINE=InnoDB  DEFAULT CHARSET=utf8 AUTO_INCREMENT=10 ;

--
-- Contraintes pour la table `role_acl`
--
ALTER TABLE `role_acl`
  ADD CONSTRAINT `role_acl_ibfk_1` FOREIGN KEY (`idrole`) REFERENCES `roles` (`idroles`) ON DELETE CASCADE ON UPDATE CASCADE;

--
-- Contraintes pour la table `role_inheritance`
--
ALTER TABLE `role_inheritance`
  ADD CONSTRAINT `role_inheritance_ibfk_1` FOREIGN KEY (`roleId`) REFERENCES `roles` (`idroles`) ON DELETE CASCADE ON UPDATE CASCADE,
  ADD CONSTRAINT `role_inheritance_ibfk_2` FOREIGN KEY (`parentRoleId`) REFERENCES `roles` (`idroles`) ON DELETE CASCADE ON UPDATE CASCADE;

--
-- Contraintes pour la table `users`
--
ALTER TABLE `users`
  ADD CONSTRAINT `users_ibfk_1` FOREIGN KEY (`idroles`) REFERENCES `roles` (`idroles`);

Bon les noms correspondent pas tout à fait à ceux que je te disais, mais l'idée est là...

A toi après dans ton interface d'admin de proposer un formulaire utilisant ces tables, pour que les administrateurs puissent ajouter, modifier ou supprimer des autorisations.

Pour la table role_acl, resource contient soir * (tout), soit truc_truc (module_controller), soit truc (module). La colonne action contient les noms des actions autorisées ou non autorisées  (par exemple "index, edit, delete") ou reste vide si on désire donner l'accès à tout. Voir la classe modèle pour comprendre les mécanismes.

Hors ligne

 

#13 29-03-2012 06:17:15

inzaghi
Membre
Date d'inscription: 09-08-2011
Messages: 74

Re: Comment créer des ACL dynamique ?

Pour les tables je fais ceci  ?

Code:

<?php



class Model_DbTable_roles extends Zend_Db_Table_Abstract
  {
    
    protected $_name = 'roles';

}
?>

j'ai eu aussi ça comme erreur

[Thu Mar 29 07:25:25 2012] [error] [client 127.0.0.1] PHP Fatal error:  Uncaught exception 'Zend_Db_Table_Exception' with message 'No adapter found for Model_DbTable_Roles' in /opt/lampp/htdocs/xampp/zf/library/Zend/Db/Table/Abstract.php:754\nStack trace:\n#0 /opt/lampp/htdocs/xampp/zf/library/Zend/Db/Table/Abstract.php(739): Zend_Db_Table_Abstract->_setupDatabaseAdapter()\n#1 /opt/lampp/htdocs/xampp/zf/library/Zend/Db/Table/Abstract.php(268): Zend_Db_Table_Abstract->_setup()\n#2 /opt/lampp/htdocs/xampp/zf/application/models/LibraryAcl.php(39): Zend_Db_Table_Abstract->__construct()\n#3 /opt/lampp/htdocs/xampp/zf/application/Bootstrap.php(17): Model_LibraryAcl->__construct()\n#4 /opt/lampp/htdocs/xampp/zf/library/Zend/Application/Bootstrap/BootstrapAbstract.php(667): Bootstrap->_initPlugin()\n#5 /opt/lampp/htdocs/xampp/zf/library/Zend/Application/Bootstrap/BootstrapAbstract.php(620): Zend_Application_Bootstrap_BootstrapAbstract->_executeResource('plugin')\n#6 /opt/lampp/htdocs/xampp/zf/library/Zend/Application/Bootstrap/BootstrapAbstract.php(584): Zend_Application_Bootstrap_BootstrapAbstr in /opt/lampp/htdocs/xampp/zf/library/Zend/Db/Table/Abstract.php on line 754

Dernière modification par inzaghi (29-03-2012 08:27:32)

Hors ligne

 

#14 29-03-2012 14:43:19

tdutrion
Administrateur
Lieu: Dijon, Paris, Edinburgh
Date d'inscription: 23-12-2009
Messages: 614
Site web

Re: Comment créer des ACL dynamique ?

Oui c'est tout à fait ça, mis à part que ton adaptateur de base de données par défaut n'est pas encore chargé au moment où le plugin est exécuté.

J'imagine que tu paramètres la base de données à l'aide de ton fichier application.ini, disons de cette façon :

Code:

resources.db.adapter = PDO_MYSQL
resources.db.params.host = localhost
resources.db.params.username = user
resources.db.params.password = pass
resources.db.params.dbname = mon_site
resources.db.params.charset = "UTF8"

Dans ce cas, il va falloir mettre une méthode permettant de charger ta bd avant celui pour les acl. Dans Bootstrap.php :

Code:

[lang=php]
protected function _initDb() {
        $pluginDb = $this->getPluginResource('db');
        $db = $pluginDb->getDbAdapter();
        $db->setFetchMode(Zend_Db::FETCH_OBJ);
        Zend_Db_Table::setDefaultAdapter($db);
        try {
            $db->getConnection();
        } catch (Zend_Db_Adapter_Exception $e) {
            die("Unable to contact the database: " . $e->getMessage());
        }
        return $db;
    }

    protected function _initAcl() {
        $acl = new App_Model_Acl();
        Zend_Controller_Front::getInstance()->registerPlugin(new App_Plugins_Acl());
        Zend_View_Helper_Navigation_HelperAbstract::setDefaultAcl($acl);
        $auth = Zend_Auth::getInstance();
        $role = (!$auth->hasIdentity()) ? 5 : $auth->getIdentity()->idroles;
    }

Par contre pour ta classe de BDD, fais attention tu as mis roles en minuscule, hors elle devrait porter une majuscule (sous Windows normalement pas de problèmes, par contre sous Linux...).

Hors ligne

 

#15 29-03-2012 16:24:21

inzaghi
Membre
Date d'inscription: 09-08-2011
Messages: 74

Re: Comment créer des ACL dynamique ?

j'ai eu ceci :
[Thu Mar 29 15:21:56 2012] [error] [client 127.0.0.1] PHP Fatal error:  Uncaught exception 'Zend_Acl_Exception' with message 'Resource 'default_error' not found' in /opt/lampp/htdocs/xampp/zf/library/Zend/Acl.php:365\nStack trace:\n#0 /opt/lampp/htdocs/xampp/zf/library/Zend/Acl.php(645): Zend_Acl->get('default_error')\n#1 /opt/lampp/htdocs/xampp/zf/library/Zend/Acl.php(508): Zend_Acl->setRule('OP_ADD', 'TYPE_ALLOW', NULL, 'default_error', NULL, NULL)\n#2 /opt/lampp/htdocs/xampp/zf/application/models/Acl.php(87): Zend_Acl->allow(NULL, 'default_error')\n#3 /opt/lampp/htdocs/xampp/zf/application/models/Acl.php(46): Model_Acl->_initRights()\n#4 /opt/lampp/htdocs/xampp/zf/application/Bootstrap.php(25): Model_Acl->__construct()\n#5 /opt/lampp/htdocs/xampp/zf/library/Zend/Application/Bootstrap/BootstrapAbstract.php(667): Bootstrap->_initAcl()\n#6 /opt/lampp/htdocs/xampp/zf/library/Zend/Application/Bootstrap/BootstrapAbstract.php(620): Zend_Application_Bootstrap_BootstrapAbstract->_executeResource('acl')\n#7 /opt/lampp/htdocs/xampp/zf/library/Zend/Application/Bootstrap/BootstrapAbstract.php(584): in /opt/lampp/htdocs/xampp/zf/library/Zend/Acl.php on line 365

Hors ligne

 

#16 29-03-2012 16:29:45

tdutrion
Administrateur
Lieu: Dijon, Paris, Edinburgh
Date d'inscription: 23-12-2009
Messages: 614
Site web

Re: Comment créer des ACL dynamique ?

Là on dirait que tu essayes d'assigner des droits sur un le controller error du module default.

Code:

[lang=php]
protected function _initRights()
{
    $this->allow(null,"default_error");

Mon code était à adapter, tu peux voir ici que je mets certains droits qui sont essentiels (genre page d'erreur) en dur dans mon code... Je l'avais dit, ce n'est pas un code parfait !

Hors ligne

 

#17 29-03-2012 16:34:05

inzaghi
Membre
Date d'inscription: 09-08-2011
Messages: 74

Re: Comment créer des ACL dynamique ?

Théocrite a écrit:

Là on dirait que tu essayes d'assigner des droits sur un le controller error du module default.

Code:

[lang=php]
protected function _initRights()
{
    $this->allow(null,"default_error");

Mon code était à adapter, tu peux voir ici que je mets certains droits qui sont essentiels (genre page d'erreur) en dur dans mon code... Je l'avais dit, ce n'est pas un code parfait !

Comment je peux l'attribuer à un formulaire ?
Je peux mettre un lien de mon code pour mieux me comprendre ?

Dernière modification par inzaghi (29-03-2012 16:44:07)

Hors ligne

 

#18 29-03-2012 17:16:00

tdutrion
Administrateur
Lieu: Dijon, Paris, Edinburgh
Date d'inscription: 23-12-2009
Messages: 614
Site web

Re: Comment créer des ACL dynamique ?

Le code en question, qui provoque ton erreur, se trouve dans ta classe de modèle ACL.

Je vois pas tout à fait pourquoi tu veux un formulaire à cet endroit là... Les formulaires doivent se trouver dans ton admin, et ils modifient ta BDD. Les infos de ta BDD sont ensuite utilisées dans ton modèle.

Hors ligne

 

#19 30-03-2012 00:21:42

inzaghi
Membre
Date d'inscription: 09-08-2011
Messages: 74

Re: Comment créer des ACL dynamique ?

je veux avoir un formulaire pour le role "admin " qui lui permettra de créer d'autres roles selon des prévilège que je choisi après ceci sera enregistré en base

Hors ligne

 

#20 30-03-2012 08:04:27

tdutrion
Administrateur
Lieu: Dijon, Paris, Edinburgh
Date d'inscription: 23-12-2009
Messages: 614
Site web

Re: Comment créer des ACL dynamique ?

C'est à dire qu'il faut pas tout confondre là...

Les erreurs que tu rencontres sont liées à la mise en place des acl sur ton appli, c'est la première chose que tu dois régler. Dans un premier temps, entre des données à la main dans ta bdd, de sorte à avoir quelques rôles et quelques actions, et fait fonctionner ton système.

Une fois cela fait, tu n'auras plus qu'à faire des formulaires et des actions classiques sur tes interfaces d'administration.

Hors ligne

 

#21 31-03-2012 05:24:04

inzaghi
Membre
Date d'inscription: 09-08-2011
Messages: 74

Re: Comment créer des ACL dynamique ?

C'est suffisant ?

Code:

 class Model_DbTable_RoleAcl extends Zend_Db_Table_Abstract
 {
    protected $_name =  'role_acl';
    
}
?>

Pour l'autre , j'ai fait ceci

Code:

<?php




class Model_Acl extends Zend_Acl
{
    private $_roles;
    private $_rolesArray = array();
    private $_roleInheritance;
    private $_modules = array();

    public function __construct()
    {
        $this->_roles = new Model_DbTable_Roles();
        $this->_roleInheritance = new Model_DbTable_RoleInheritance();
        $frontController = Zend_Controller_Front::getInstance();
        $this->_modules = array_keys($frontController->getControllerDirectory());

        $this->_initRessources();
        $this->_initRoles();
        $this->_initRights();

        Zend_Registry::set('Acl', $this);
    }

    protected function _initRessources()
    {
        $frontController = Zend_Controller_Front::getInstance();
        foreach($frontController->getControllerDirectory() as $module => $controllerPath) {
            foreach(glob($controllerPath.'/*Controller.php') as $controller) {
                $this->addResource(new Zend_Acl_Resource($module.'_'.strtolower(basename($controller,'Controller.php'))));
            }
        }
    }

    protected function _initRoles()
    {
        /* get roles from db */
        foreach ($this->_roles->fetchAll() as $role) {
            $this->_rolesArray[$role->idroles] = $role;
        }
        foreach ($this->_roles->fetchAll() as $role) {
            if(!$this->hasRole($role->idroles)) $this->setNewRole($role);
        }
    }

    protected function setNewRole($role) {
        $inheritance = $this->_roleInheritance->fetchAll('roleId="'.$role->idroles.'"');
        if(count($inheritance) > 0) {
            foreach ($inheritance as $i) {
                if(!$this->hasRole($i->parentRoleId)) $this->setNewRole($this->_rolesArray[$i->parentRoleId]);
                $this->addRole(new Zend_Acl_Role($role->idroles),$this->_rolesArray[$i->parentRoleId]->idroles);
            }
        } else {
            $this->addRole(new Zend_Acl_Role($role->idroles));
        }
    }


    protected function _initRights()
    {
      //  $this->allow(null,"default_error");
        $acl = new Model_DbTable_RoleAcl();
        foreach ($acl->fetchAll() as $value) {
            try {
                if($this->has($value->resource)):
                    if($value->permission == 'allow') $this->allow($value->idrole,$value->resource,!empty($value->actions)?explode(", ",$value->actions):null);
                    else $this->allow($value->idrole,$value->resource,!empty($value->actions)?explode(", ",$value->actions):null);
                elseif($value->resource == '*'):
                    if($value->permission == 'allow') $this->allow($value->idrole,NULL);
                    else $this->allow($value->idrole,NULL);
                elseif(in_array($value->resource, $this->_modules)):
                    $frontController = Zend_Controller_Front::getInstance();
                    $dir = $frontController->getControllerDirectory();
                    foreach(glob($dir[$value->resource].'/*Controller.php') as $controller) {
                        $this->allow($value->idrole,$value->resource.'_'.strtolower(basename($controller,'Controller.php')));
                    }
                endif;
                $auth = Zend_Auth::getInstance()->setStorage(new Zend_Auth_Storage_Session('auth'));
                if($auth->hasIdentity()) {
                    $this->allow($auth->getIdentity()->idroles,'book','edit');
                    $this->allow($auth->getIdentity()->idroles,'books','liste');
                }
            } catch (Exception $e) { /** @todo log errors and display them in admin */ }
        }
    }

    public function isAllowed($role = null, $resource = null, $privilege = null) {
        if($this->hasRole($role) and $this->has($resource)) {
            return parent::isAllowed($role, $resource, $privilege);
        }
        $frontController = Zend_Controller_Front::getInstance();
        $modules = $frontController->getControllerDirectory();
        if(isset($modules[$resource])) {
            foreach(glob($modules[$resource].'/*Controller.php') as $controller) {
                if($this->has($resource.'_'.strtolower(basename($controller,'Controller.php'))) and !parent::isAllowed($role,$resource.'_'.strtolower(basename($controller,'Controller.php')))) return false;
            }
            return true;
        }
        return false;
    }
}
?>

Dernière modification par inzaghi (31-03-2012 05:25:07)

Hors ligne

 

#22 31-03-2012 09:56:43

tdutrion
Administrateur
Lieu: Dijon, Paris, Edinburgh
Date d'inscription: 23-12-2009
Messages: 614
Site web

Re: Comment créer des ACL dynamique ?

Bonjour,

Pour savoir si c'est bon, le mieux c'est de tester...

Faut que tu testes tout ça, et si ça marche tu peux passer à la mise en place des formulaires, maintenant je t'ai donné tout le code à adapter, donc pour le reste je sais pas si c'est ton métier ou quoi développeur mais tu dois être en mesure de te débrouiller tout seul.

Hors ligne

 

#23 31-03-2012 22:22:48

inzaghi
Membre
Date d'inscription: 09-08-2011
Messages: 74

Re: Comment créer des ACL dynamique ?

Théocrite a écrit:

Bonjour,

Pour savoir si c'est bon, le mieux c'est de tester...

Faut que tu testes tout ça, et si ça marche tu peux passer à la mise en place des formulaires, maintenant je t'ai donné tout le code à adapter, donc pour le reste je sais pas si c'est ton métier ou quoi développeur mais tu dois être en mesure de te débrouiller tout seul.

Oui c'est ce que j'ai fais mais j'ai cette erreur
Uncaught exception 'Zend_Controller_Action_Exception' with message 'Action "deny" does not exist and was not trapped in __call()' in /opt/lampp/htdocs/xampp/zf/library/Zend/Controller/Action.php:485\nStack trace:\n#0 /opt/lampp/htdocs/xampp/zf/library/Zend/Controller/Action.php(515): Zend_Controller_Action->__call('denyAction', Array)\n#1 /opt/lampp/htdocs/xampp/zf/library/Zend/Controller/Dispatcher/Standard.php(295): Zend_Controller_Action->dispatch('denyAction')\n#2 /opt/lampp/htdocs/xampp/zf/library/Zend/Controller/Front.php(954): Zend_Controller_Dispatcher_Standard->dispatch(Object(Zend_Controller_Request_Http), Object(Zend_Controller_Response_Http))\n#3 /opt/lampp/htdocs/xampp/zf/library/Zend/Application/Bootstrap/Bootstrap.php(97): Zend_Controller_Front->dispatch()\n#4 /opt/lampp/htdocs/xampp/zf/library/Zend/Application.php(366): Zend_Application_Bootstrap_Bootstrap->run()\n#5 /opt/lampp/htdocs/xampp/zf/public/index.php(27): Zend_Application->run()\n#6 {main}\n  thrown in /opt/lampp/htdocs/xampp/zf/library/Zend/Controller/Action.php on line 485
[Sat Mar 31 03:58:12 2012] [error] [client 127.0.0.1] PHP Fatal error:  Uncaught exception 'Zend_Controller_Action_Exception' with message 'Action "deny" does not exist and was not trapped in __call()' in /opt/lampp/htdocs/xampp/zf/library/Zend/Controller/Action.php:485\nStack trace:\n#0 /opt/lampp/htdocs/xampp/zf/library/Zend/Controller/Action.php(515): Zend_Controller_Action->__call('denyAction', Array)\n#1 /opt/lampp/htdocs/xampp/zf/library/Zend/Controller/Dispatcher/Standard.php(295): Zend_Controller_Action->dispatch('denyAction')\n#2 /opt/lampp/htdocs/xampp/zf/library/Zend/Controller/Front.php(954): Zend_Controller_Dispatcher_Standard->dispatch(Object(Zend_Controller_Request_Http), Object(Zend_Controller_Response_Http))\n#3 /opt/lampp/htdocs/xampp/zf/library/Zend/Application/Bootstrap/Bootstrap.php(97): Zend_Controller_Front->dispatch()\n#4 /opt/lampp/htdocs/xampp/zf/library/Zend/Application.php(366): Zend_Application_Bootstrap_Bootstrap->run()\n#5 /opt/lampp/htdocs/xampp/zf/public/index.php(27): Zend_Application->run()\n#6 {main}\n  thrown in /opt/lampp/htdocs/xampp/zf/library/Zend/Controller/Action.php on line 485, referer: http://localhost/xampp/zf/public/authentification/login

Hors ligne

 

#24 31-03-2012 22:28:33

tdutrion
Administrateur
Lieu: Dijon, Paris, Edinburgh
Date d'inscription: 23-12-2009
Messages: 614
Site web

Re: Comment créer des ACL dynamique ?

Encore une fois c'est toi qui copie sans regarder et sans adapter... Dans ton plugin d'acl, on fait suivre sur une action deny (en début de plugin, on définit des arrays de redirection, dont no_acl qui est celui qui te pose problème...).

C'est dans quel cadre ton projet ? C'est un truc pro ?

Hors ligne

 

#25 31-03-2012 22:30:06

inzaghi
Membre
Date d'inscription: 09-08-2011
Messages: 74

Re: Comment créer des ACL dynamique ?

Théocrite a écrit:

Encore une fois c'est toi qui copie sans regarder et sans adapter... Dans ton plugin d'acl, on fait suivre sur une action deny (en début de plugin, on définit des arrays de redirection, dont no_acl qui est celui qui te pose problème...).

C'est dans quel cadre ton projet ? C'est un truc pro ?

Dans le cadre de mon PFE

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