Zend FR

Consultez la FAQ sur le ZF avant de poster une question

Vous n'êtes pas identifié.

#1 29-01-2014 19:48:07

Splyf
Membre
Date d'inscription: 24-10-2013
Messages: 115

Route, child_routes, layout et erreur 404

Re bonjour,
encore moi ! (dsl je squoite un peut :p)
cette foi-ci avec une galère sur les routes (bientôt, j'aurai fait le tour^^)

Voila ce que j'essaye de faire:

j'ai deux layout, un sur le domaine myhost.fr/, et un pour myhost.fr/admin.
le changement de layout ce fait dans un module Admin, via la fonction onBootstrap, au déclenchement de l’événement MVCEvent:EVENT_ROUTE.

J'ai en suite divers module, qui me gère a la foi l'admin et le front. avec différente vue et controller (sur les conseilles avisé de Orkin ^^).

J'y accède avec l'url
myhost.fr/admin/module1.
myhost.fr/admin/module2[controller][action][params].
ect
mais quand je fait
myhost.fr/admin/nimporte-quoi-qui-nexiste-pas
Je veut que se sois le layout de l'admin qui affiche l'érreur 404, et non le layout du module application!

J'y arrive, mais alors c'est qiue plus aucune adresse n'est accessible xD

voici ma config:

dans mes  module:

Code:

[lang=php]
'router' => array(
        'routes' => array(
            'admin' => array(
                'may_terminate' => true,
                'child_routes' => array(
                    'module1' => array(
                        'type' => 'segment',
                        'options' => array(
                            'route' => '/module1[/][:action][/:id]',
                            'constraints' => array(
                                'action' => '[a-zA-Z][a-zA-Z0-9_-]*',
                                'id' => '[0-9]+',
                            ),
                            'defaults' => array(
                                'controller' => 'Module1\Controller\Admin',
                                'action' => 'index',
                            ),
                        ),
                    )
                )
            )
        ),
    ),

dans l'admin,
1er cas, la config précédente marche, mais c'est le layout du module application qui s'affiche en cas de 404:

Code:

[lang=php]
'router' => array(
        'routes' => array(
            'admin' => array( 
                'type' => 'segment',
                'options' => array(
                    'route' => '/admin', 
                    'defaults' => array(
                        'controller' => 'Admin\Controller\Admin',
                        'action' => 'index',
                    ),
                ), 
            ),
        ),
    ),

2eme cas...résultat inverse:

Code:

[lang=php]
'router' => array(
        'routes' => array(
            'admin' => array( 
                'type' => 'segment',
                'options' => array(
                    'route' => '/admin[/][:action][/:id]', 
                    'constraints' => array(
                        'action' => '[a-zA-Z][a-zA-Z0-9_-]*',
                        'id' => '[0-9]+',
                    ),
                    'defaults' => array(
                        'controller' => 'Admin\Controller\Admin',
                        'action' => 'index',
                    ),
                ),
            ),
        ),
    ),

Et oui car je suis un peut chian, j'aimerai avoir des action spécifique a l'admin et défini dans son controller - tel que /admin/index, admin/login, ect smile

J'ai essayer beaucoup de chose, je me retrouve toujours dans l'un ou l'autre cas.

Voila...je cherche peut être la lune...

Hors ligne

 

#2 30-01-2014 04:50:35

Alkaest
Nouveau membre
Date d'inscription: 30-01-2014
Messages: 8

Re: Route, child_routes, layout et erreur 404

Bonjour

Je n'ai pas très bien compris...

Dans le premier cas, les routes fonctionnent mais le layout pour la 404 n'est pas le bon; et dans le deuxième cas aucune route ne fonctionne mais cette fois-ci le layout est le bon, c'est ça?

Pourrais-tu donner le schéma de ton arborescence pour comprendre un peu mieux ce que tu cherches à faire? Les modules avec les controllers devraient suffire.

Hors ligne

 

#3 30-01-2014 10:07:38

Splyf
Membre
Date d'inscription: 24-10-2013
Messages: 115

Re: Route, child_routes, layout et erreur 404

Bonjour,

oui c'est exactement sa le problème.

Arborescences  (j'ai rajouter quelque vue de l'admin pour aider un peut plus):

Code:

|Module
|--Admin
|-----src/controller
|----------adminController.php
|-----view/
|----------admin/
|--------------admin/index.phtml | login.phtml
|--------------layout/layout.phtml
|--------------error/404.phtml


|--Catalogue
|-----src/controller
|----------adminController.php
|----------frontController.php
|----------ajaxController.php


|--User
|-----src/controller
|----------adminController.php
...

|--Application
-> laissé tel quel - pour le moment

Amin: gère le layout du backoffice, l'authentification et quelque service. Dépend du module User, forcément.
Catalogue: contient - tel que d'autre- une partie du model de l'applications.

Ainsi, je peut retirer le module Catalogue sans tout faire planté, et je n'ai qu'a changer le fichier de config pour le mettre dans une autre application.

J'espère que c'est plus clair comme sa ^^

Dernière modification par Splyf (30-01-2014 10:11:57)

Hors ligne

 

#4 30-01-2014 10:18:04

Orkin
Administrateur
Lieu: Paris
Date d'inscription: 09-12-2011
Messages: 1261

Re: Route, child_routes, layout et erreur 404

Salut ! Décidément tu ne nous quittes plus en ce moment smile !

J'ai pas trop regardé tes routes parce qu'elles n'ont pas d'impacts sur la modification ou non du layout. Et l'arborescence de tes fichiers n'a pas d'impacts non plus puisque c'est vraiment lié au worflow MVC du ZF2.

En cas d'erreur sur le routing c'est dispatch.error qui est lancé comme évènement et tu ne passes pas dans MvcEvent::EVENT_ROUTE. Donc ton code est jamais exécuté. Pour résoudre ton problème il te suffit de changer l'évènement que tu écoutes par MvcEvent::EVENT_RENDER puisque c'est vraiment au moment du rendu que tu auras besoin de faire la modification wink.

Hors ligne

 

#5 30-01-2014 11:56:55

Splyf
Membre
Date d'inscription: 24-10-2013
Messages: 115

Re: Route, child_routes, layout et erreur 404

Et oui j'ai bien l'intention de mettre le temps que j'ai a profit  pour  maîtriser ZF 2 aux max smile

Le probleme du event_render, c'est que je n'arrive pas a récupe la route

admin/module.php (simplifié)

Code:

[lang=php]
public function onBootstrap(MvcEvent $e) {

        $app = $e->getParam('application'); 

        $em = $app->getEventManager();  
        $em->attach(MvcEvent::EVENT_RENDER,
                function($e)  {
                    $this->setLayout($e);
                });
    }

    public function setLayout(MvcEvent $e) {
        $matches = $e->getRouteMatch();  
        $matchedRouteName = $matches->getMatchedRouteName();  //ligne 32
        if (preg_match('#^admin#', $matchedRouteName)) {
            $viewModel = $e->getViewModel();
          
            $viewModel->setTemplate('admin/layout');

        }
    }

Avec event_render, $e->getRouteMatch() retourn null a priorie

Fatal error: Call to a member function getMatchedRouteName() on a non-object in /my/path/Admin/Module.php on line 38

Bon je suis sur un autre problème, je creuserai plus tard, sauf si tu vous  déjà la solution ^^

EDIT:
Je pourrai utilisé lobject Request pour contrôler si il y a admin dans mon chemin...mais la le code est simplifié et je controle aussi si l'user est conecter et le cas échéant, je change le controller et l'action de la route pour rediriger sur la page de login.
Dite moi si vous voulez ce code aussi...

Dernière modification par Splyf (30-01-2014 12:32:21)

Hors ligne

 

#6 30-01-2014 14:09:05

Orkin
Administrateur
Lieu: Paris
Date d'inscription: 09-12-2011
Messages: 1261

Re: Route, child_routes, layout et erreur 404

Héhé tu as bien raison smile !

En fait c'est normal que getRouteMatch() renvoie null en cas d'erreur sur l'url puisqu'il n'y a pas de route qui match dans ta configuration. Dans ce cas tu dois effectuer une vérification au niveau de l'url directement je ne vois pas comment faire autrement. Normalement c'est jamais censé arriver parce que si c'est le cas ça veut dire que l'admin essaie de bidouiller les urls ... Dans ce cas moi je pars du principe que c'est un utilisateur qui veut faire le malin je me pose pas de question, je renvoie directement sur home (et si tu veux vraiment éviter ce genre de chose tu détruis sa session). Normalement quelqu'un qui utilise correctement le site ne tombera pas sur une 404. Même s'il essaie d'aller sur un article qui a été supprimé par exemple toi t'es censé contrôler avant d'afficher la page si l'article existe et rediriger s'il n'existe pas.

Donc pour résumer moi je testerais si la méthode getRouteMatch() retourne null ou non. Et à partir de là tu tiens compte si l'utilisateur est connecté ou pas. S'il n'est pas connecté dans ce cas aucune raison de changer le layout puisqu'un invité n'est pas censé accéder à l'espace d'aministration. Soit il est connecté et là tu tests s'il est admin ou non. S'il est admin tu affiches le layout admin sinon tu fais rien.
Il reste toujours un petit soucis c'est dans le cas où l'utilisateur est administrateur et qu'il accède à une 404 ailleurs que sur l'espace admin ... Pour ce cas tu peux récupérer soit le router soit la requete ($event->getRouter() ou $event->getRequest()) et récupérer l'uri pour la traiter si besoin.

Pour vérifier si l'utilisateur est connecté c'est super simple :

Code:

[lang=php]
/** @var AuthenticationService $authenticationService */
        $authenticationService = $this->getServiceLocator()->get('Zend\Authentication\AuthenticationService');
        if ($authenticationService->hasIdentity()) {
            // ton code
        }

Hors ligne

 

#7 30-01-2014 16:08:17

Splyf
Membre
Date d'inscription: 24-10-2013
Messages: 115

Re: Route, child_routes, layout et erreur 404

Je suis dacord, normalement si l'utilisateur ne fait pas nimp', pas de raison qu'il tombe sur un 404 dans l'admin.
Mais mon projet est une sorte de  laboratoire, j'essaye d'imaginer toute sorte de situation pour farfouillé le plus possible ^^.

Un des objectif de tout sa était aussi de comprendre les routes et child_routes:
Je vais tenter ta solution mais est-ce que la route parente peut fonctionné si ses enfants ne sont pas "matcher" dans l'URL...
Il semble que non?
(j'avance javance) ^^

EDIT:
(édit supprimer pour plus de clarté, voir l'edit 2 suivant smile )

Edit 2:
BINGOOOOO!!!
pardon mon entousiasme, mas j'ai trouver:

il suffit de rajouter un child route...sans racine! big_smile
dans l'admin :

Code:

[lang=php]
'router' => array(
        'routes' => array(
            'admin' => array(
                'type' => 'literal',
                'options' => array(
                    'route' => '/admin', 
                ),
                'may_terminate' => true,
                    'child_routes' => array(
                        'admin' => array(
                            'type' => 'segment',
                            'options' => array(
                                'route' => '[/][:action]',
                                'constraints' => array(
                                    'action' => '[a-zA-Z][a-zA-Z0-9_-]*',
                                ),
                                'defaults' => array(
                                    'controller' => 'Admin\Controller\Admin',
                                    'action' => 'index',
                                ),
                            ),
                        )
                    )
            ),
        ),
    ),

Ce qui résoud même mon problème de 404 !!
pendant un moment je commençais a remettre en cause mon architecture...mais ZF2 est genial, pourquoi je m'y suis pas mis avant? a j'avais pas le temps c'est vrai big_smile

Dernière modification par Splyf (30-01-2014 18:47:01)

Hors ligne

 

#8 31-01-2014 03:51:20

Alkaest
Nouveau membre
Date d'inscription: 30-01-2014
Messages: 8

Re: Route, child_routes, layout et erreur 404

Orkin a écrit:

En cas d'erreur sur le routing c'est dispatch.error qui est lancé comme évènement et tu ne passes pas dans MvcEvent::EVENT_ROUTE. Donc ton code est jamais exécuté. Pour résoudre ton problème il te suffit de changer l'évènement que tu écoutes par MvcEvent::EVENT_RENDER puisque c'est vraiment au moment du rendu que tu auras besoin de faire la modification wink.

Bonjour,

Ce message me rend fou...

Orkin a écrit:

En cas d'erreur sur le routing c'est dispatch.error qui est lancé comme évènement

1 : En cas d'erreur sur le ROUTING, c'est DISPATCH.error qui est lancé???  Ça me semble complètement incohérent...

Orkin a écrit:

et tu ne passes pas dans MvcEvent::EVENT_ROUTE

2 : Si je suis la logique de Zend\Mvc\Application, on passe au contraire nécessairement dans MvcEvent::EVENT_ROUTE, mais c'est justement lors de cet event que l'erreur de routing est détectée (provoquant un court-circuit), ce qui nous amène à forcer la réponse de déclenchant EVENT_RENDER puis EVENT_FINISH. Non?

Dernière modification par Alkaest (31-01-2014 03:55:14)

Hors ligne

 

#9 31-01-2014 10:16:11

Orkin
Administrateur
Lieu: Paris
Date d'inscription: 09-12-2011
Messages: 1261

Re: Route, child_routes, layout et erreur 404

Alkaest a écrit:

Ce message me rend fou...

Te mets pas dans des états pareils :p !

Alkaest a écrit:

1 : En cas d'erreur sur le ROUTING, c'est DISPATCH.error qui est lancé???  Ça me semble complètement incohérent...

Non ...

Code:

[lang=php]
public function onRoute($e)
    {
        $target     = $e->getTarget();
        $request    = $e->getRequest();
        $router     = $e->getRouter();
        $routeMatch = $router->match($request);

        if (!$routeMatch instanceof Router\RouteMatch) {
            $e->setError(Application::ERROR_ROUTER_NO_MATCH);

            $results = $target->getEventManager()->trigger(MvcEvent::EVENT_DISPATCH_ERROR, $e);
            if (count($results)) {
                $return  = $results->last();
            } else {
                $return = $e->getParams();
            }
            return $return;
        }

        $e->setRouteMatch($routeMatch);
        return $routeMatch;
    }

Donc on a bien EVENT_DISPATCH_ERROR de lancé en cas d'erreur sur le routing. Effectivement j'ai pris le raccourcis de dire que l'évènement n'était pas lancé alors que ce n'est pas le cas mais on ne peut pas le capturer puisqu'il est court-circuité. Donc au final on a pas la main dessus. Mais tu as raison j'aurai pas du prendre ce raccourcis :p !

Alkaest a écrit:

2 : Si je suis la logique de Zend\Mvc\Application, on passe au contraire nécessairement dans MvcEvent::EVENT_ROUTE, mais c'est justement lors de cet event que l'erreur de routing est détectée (provoquant un court-circuit), ce qui nous amène à forcer la réponse de déclenchant EVENT_RENDER puis EVENT_FINISH. Non?

L'évènement EVENT_ROUTE déclenche EVENT_DISPATCH_ERROR lorsque la route n'est pas trouvée et dans ce cas on ne peut donc pas intervenir dessus. On peut donc dans ce cas capturer EVENT_DISPATCH_ERROR. Le problème c'est qu'il est lancé uniquement quand il y a une erreur (pour utiliser le contrôleur permettant l'affichage de la 404). Le problème c'est que si l'on souhaite modifier le layout lorsqu'il n'y a pas d'erreurs ça n'est pas le bon évènement à capturer. Il nous reste donc EVENT_RENDER et EVENT_FINISH. EVENT_FINISH est lancé quand la boucle MVC est terminée donc si je ne dis pas de bêtises il est trop tard pour modifier le layout. Il ne nous reste plus qu'EVENT_RENDER.

Hors ligne

 

#10 01-02-2014 11:04:02

Bouks
Membre
Lieu: Paris
Date d'inscription: 31-08-2012
Messages: 241

Re: Route, child_routes, layout et erreur 404

Orkin a écrit:

Dans ce cas moi je pars du principe que c'est un utilisateur qui veut faire le malin je me pose pas de question, je renvoie directement sur home (et si tu veux vraiment éviter ce genre de chose tu détruis sa session).

+1

Orkin a écrit:

Normalement quelqu'un qui utilise correctement le site ne tombera pas sur une 404. Même s'il essaie d'aller sur un article qui a été supprimé par exemple toi t'es censé contrôler avant d'afficher la page si l'article existe et rediriger s'il n'existe pas.

Et envoyer un code 410 si possible. smile


22914720

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