0
votes

I am having problem with adding custom routing into my application. Zend Framework 1:

I have already working application with default Zend routing. I have a lot of controllers and for some of them I want to use friendly urls, for example: domain.com/cities/edit/id/3 to domain.com/cities/edit/abu-dhabi

There are some controllers to switch into that url (in that format).

I tried to configure it by ini file:

resources.router.routes.slugurl.route = /:controller/:action/:slug

And also by Bootstrap method:

protected function _initSlugRouter()
{
    $this->bootstrap('FrontController');
    $router = $this->frontController->getRouter();
    $route = new Zend_Controller_Router_Route('/:controller/:action/:slug/',
        array(
            'controller' => 'slug',
            'action' => 'forward',
            'slug' => ':slug'
        )
    );
    $router->addRoute('slug',$route);

}

The main problem - with ini configuration - request goes directly to controller city (not slug). Second one (bootstrap) - also executes the city controller, but the default routing not working as it was, I am not able to execute: domain.com/cities/ but domain.com/cities/index/ works. The error without action defined:

Action "forward" does not exist and was not trapped in __call()

I can monitor the "slug" in controllers/move check into some library, but I would like to do it only with routing - that way looks much better for me.. Please, how to solve that issue?


edit with summary of solution Thank you Max P. for interesting. I solved it at last - in last 2 minutes:) I had wrong rules at application.ini with routing. Right now it is defined that:

resources.router.routes.slugurl.route = /:controller/:action/:slug
resources.router.routes.slugurl.defaults.controller = :controller
resources.router.routes.slugurl.defaults.action = :action
resources.router.routes.slugurl.defaults.slug = :slug

The controller is defined like that:

class CitiesController extends Crm_Abstract

The Crm_Abstract has code:

<?php

class Crm_Abstract extends Zend_Controller_Action {

    public function __construct(\Zend_Controller_Request_Abstract $request, \Zend_Controller_Response_Abstract $response, array $invokeArgs = array()) {

        $params = $request->getParams();

        if (!empty($params['slug'])) {
            $modelSlug = Crm_Helper_Slug::getInstance();
            $parameters = $modelSlug->redirectRequest($request);
            if ($parameters !== false) {
                foreach ($parameters as $key => $value) {
                    $request->setParam($key, $value);
                }
            }
        }
        parent::__construct($request, $response, $invokeArgs);

    }

    public function __call($methodName, $args) {

        parent::__call($methodName, $args);
    }


}

The slug helper get parameters for slug at defined controller. The url to access the slug is defined/calculated in place of $this->url - to $this->slug and there rest of code is done in slug helper. I am not sure if my solution is 100% sure, because that is my first time with routing.

The major thing is that - I just needed to change Zend_Controller_Action to Crm_Abstract which extends the Zend_Controller_Action. Single line - no additional custom code in each controller.

1
If to comment this route what error appear for url domain.com/cities/edit/abu-dhabi? - Max P.
I will add error just when I will get valid error code - I am not able to format it at comment :( - Mik
I'm still unable to understand the ZF routing - always only one thing not working well - when I am adding routing: resources.router.routes.slugurl.route = /:controller/:action/:slug resources.router.routes.slugurl.defaults.controller = :controller resources.router.routes.slugurl.defaults.action = :action resources.router.routes.slugurl.defaults.slug = :slug I am unable to access url: domain.com/developers/ - error code: Action "action" does not exist and was not trapped in __call() - It looks like adding that route rule - destroys default routing, but I want it keep. - Mik

1 Answers

1
votes

I created two route rules:

resources.router.routes.slugurl.type = "Zend_Controller_Router_Route"
resources.router.routes.slugurl.route = /:controller/:action/:slug/
resources.router.routes.slugurl.defaults.module = "default"
resources.router.routes.slugurl.defaults.controller = :controller
resources.router.routes.slugurl.defaults.action = :action
resources.router.routes.slugurl.defaults.slug = :slug


resources.router.routes.plain1.route = "/:controller/:action/"
resources.router.routes.plain1.defaults.module = "default"
resources.router.routes.plain1.defaults.controller = "index"
resources.router.routes.plain1.defaults.action = "index"

And for now that works fine. Bad thing - I don't understand routing (htaccess rules), but the time spent on that problem and solve it is better than modify all controllers...