For SEO purpose, I have to put all form data into an URL. Here's the routing :
Router::connect('/liste-voitures/:marque/:modele/:categorie/:energie',
array(
'controller' => 'vehicules',
'action' => 'index',
),
array(
'pass' => array(
'marque',
'modele',
'categorie',
'energie'
)
)
);
So in my index action I've built an array with the values and pass it to the redirect function to match with the route :
$urlbuilding = array(
'action' => 'index',
'marque' => 'volvo-3',
'modele' => 'C30-2',
'categorie' => 'citadine',
'energie' => 'diesel'
);
$this->redirect($urlbuilding);
This is working fine as I get to the URL :
/liste-voitures/volvo-3/C30-2/citadine/diesel/
Except for the pagination. The page numbers are pointing to the URL :
/vehicules/index/volvo-3/C30-2/citadine/diesel/page:2/sort:Vehicule.recommande/direction:desc
and it should be
/liste-voitures/volvo-3/C30-2/citadine/diesel/page:2/sort:Vehicule.recommande/direction:desc
I tried to change the url by setting Pagination options :
$this->Paginator->options = array(
'url' => array(
'action' => 'index',
'marque' => $this->request->params['marque'],
'modele' => $this->request->params['modele'],
'categorie' => $this->request->params['categorie'],
'energie' => $this->request->params['energie']
)
);
But it didn't work better.
I then tried to add a route with a wildcard :
Router::connect('/liste-voitures/:marque/:modele/:categorie/:energie/*',
array(
'controller' => 'vehicules',
'action' => 'index',
),
array(
'pass' => array(
'marque',
'modele',
'categorie',
'energie',
'page',
'sort',
'direction'
)
)
);
But It did'nt work. And I'm not yet trying to get the page, sort and direction values prettier as in
/liste-voitures/volvo-3/C30-2/citadine/diesel/2/Vehicule.recommande/desc
... but that would be my next step ;)
Do anyone would mind telling me if I'm doing something wrong ? It's been days since I last had the feeling to move forward with this project. I would be very grateful if someone could drive me on the right way ! :)
SEO urls and Cakephp pagination urls are two different sides of a coin!
For urls use your own logic and pass parameters to pagination settings, in your views you can create seo friendly urls and will be able to use paginator component of cakephp.
Router::connect('/liste-voitures/:marque/:modele/:categorie/:energie/:page/:sort/:direction',
array(
'controller' => 'vehicules',
'action' => 'index',
),
array(
'pass' => array(
'marque',
'modele',
'categorie',
'energie',
'page',
'sort',
'direction'
)
)
);
This should be your routing and use your own logic too create pagination urls, do not use paginate helper.
Related
I'm trying to create a route in Zend 1.12 with a optional segment, but i don't know and i can't find a way to do it.
The situation is, i have the route:
$routes['news'] = array(
'route' => '/news/page/:page',
'defaults' => array(
'module' => 'default',
'controller' => 'news',
'action' => 'index',
'page' => 1,
),
'reqs' => array(
'page' => '([2-9][0-9]*)',
),
);
But i need the segment of the route /page/:page does not appear when the page is 1
Example:
Page = 1 -> /news
Page = 2 -> /news/page/2
Any ideas how can i do it?
I'm trying to setup the following routing in cakePHP 2.3:
domain/news/slug
I've followed the cookbook guidelines on routing and the route that gets created is correct. The problem I run into is that when selecting the link I get the 'Missing Method in NewsController' error message.
Here's what I've configured:
Router::connect(
'/news/:slug/',
array('controller' => 'news', 'action' => 'view'),
array(
'pass' => array('slug'),
'slug' => '[^_]+'
)
);
I'm passing in the slug with a regular expression (any string that does not include an underscore).
This is my link in the index page:
<?php echo $this->Html->link(
$news['News']['title'],
array(
'controller' => 'news',
'action' => 'view',
'slug' => $news['News']['slug']
)
); ?>
As mentioned, the URL is built correctly, and looks like this: /news/test-slug-news-story
But when I click on it I get the 'Missing Method in NewsController' error message
Is it obvious what I'm missing, cause I've looked at this too long to be able to see it.
Thanks, Paul
You can try this one:
<?php
// Routing code
Router::connect('/news/:slug/',
array(
'controller' => 'news',
'action' => 'view'
),
array(
'slug' => '[a-zA-Z0-9_-]+'
)
);
?>
<?php
// HTML Link code.
echo $this->Html->link(
$news['News']['title'],
array(
'controller' => 'news',
'action' => 'view',
'slug' => $news['News']['slug']
)
);
?>
If it is not working for you please let me know :)
Thanks
As mentioned above, I discovered that by having a backslash after 'slug' in the route setting, the controller interprets the ':slug/' as the controller action.
One of those 'doh' moments.
Code should look like this:
Router::connect(
'/news/:slug',
array('controller' => 'news', 'action' => 'view'),
array(
'pass' => array('slug'),
'slug' => '[a-zA-Z0-9_-]+'
)
);
i need to route urls like in zf1.
in particular i need that these urls will be automatically redirect to appropriate actions without specify a new route every time.
/site/getData
/site/getData?param=5&par2=test
/site/getOther
...
So a segment route doesn't work, i've tried a Literal route but i can't reach a working solutions.
Anyone can help me?
Thanks a lot
This should be solved by a pretty default segment route like the one provided in the documentation.
'type' => 'Zend\Mvc\Router\Http\Segment',
'options' => array(
'route' => '/:controller[/:action]',
'constraints' => array(
'controller' => '[a-zA-Z][a-zA-Z0-9_-]+',
'action' => '[a-zA-Z][a-zA-Z0-9_-]+',
),
'defaults' => array(
'controller' => 'default-controller-alias',
'action' => 'index',
),
)
Now if you set up your controller names like the following:
'controllers' => array(
'invokables' => array(
'sites' => 'Namespace\Controller\SitesController',
'other' => 'Namespace\Controller\OtherController'
Then you should be able to achieve exactly what you want. And to create params to your route, you simply use the ViewHelper correctly ;)
$this->url('routename',
array(
'controller' => 'site',
'action' => 'getData'
),
array (
'query' => array(
'param1' => 'foo',
'param2' => 'bar',
'paramN' => 'baz',
)
)
)
This is a bit cryptic, especially on day 1. Could use some help if you dont mind. Controller is search, on action_query($search_term)
So right now its /search/query/some query?page=1 (this is without a route)
Need to get it setup in this format..
/search/some query/1
1 being the page with pagination
$pagination = Pagination::factory(array(
'current_page' => array('source' => 'route', 'key' => 'page'),
'total_items' => $count,
'items_per_page' => 100,
'view' => 'pagination/basic',
));
With Route
Route::set('page', '<controller>/<action>/<search_term>(/<page>)')
->defaults(array(
'action' => 'query',
'search_term' => '[a-zA-Z0-9 ]',
'controller' => 'search',
'action' => 'page',
'page' => '1',
)
);
I have a pagination working and my route looks like:
Route::set('comments', 'welcome/index(/<page>)', array('page' => '[0-9]+'))
->defaults(array(
'controller' => 'welcome',
'action' => 'index'
));
Also, I think you are missing a parameter when creating the paginator, which is:
'uri_segment' => 'page', // pass a string as uri_segment to trigger former 'label' functionality.
I'm trying to make a Router that can respond to this structure:
module/controller/action/id and module/controller/action/page
The only difference is is 'id' or 'page'. I'm using this code:
$routeAdmin = new Zend_Controller_Router_Route(
'administrador/:controller/:action/:id/:pg',
array(
'module' => 'administrador',
'controller' => 'index',
'action' => 'index',
'id' => 0,
'pg' => 1
),
array(
'id' => '\d+',
'pg' => '\d+'
)
);
$router->addRoute('administrador', $routeAdmin);
The problem is that in some situations i want:
'http://www.domain.cl/administrador/productos/2' => (module=>administrador, controller=>productos,page=>2) but with the router 'administrador' result in 'http://www.domain.cl/administrador/productos/index/0/2' (module=>administrador, controller=>productos,action=>index,id=>0,page=>2)
I'm very confused about how it works for cases like this. I tried to make two router where the first only have 'id' param and the other 'page' param. And from url helper use it like:
$this->url(array('module' => 'administrador', 'controller' => 'productos', 'action' => 'index', 'id' => 0), 'administradorId');
$this->url(array('module' => 'administrador', 'controller' => 'productos', 'action' => 'index', 'page' => 1), 'administradorPg');
But when I used the routers always select the last one added to the router ($router->addRoute('routerIdentifier', $route);)
Thanks
I have had a similar issue and I got around this by defining just one route like this
$routeAdmin = new Zend_Controller_Router_Route(
'administrador/:controller/:action/:id/:pg',
array(
'module' => 'administrador',
'controller' => 'index',
'action' => 'index',
'id' => 0
),
array(
'id' => '\d+'
)
);
$router->addRoute('administrador', $routeAdmin);
In your actions you'd then need to get the id and check for it somewhere where that id might be, for example if you were in /administrador/events/view/1 then you might look in the events table or if you were in /administrador/pages/view/1 then you would look for a page.
But the problems really start when the id could be either an event or a page in a given controller and action. The only real way around this is explicitly set the type of id your using for example
/administrador/events/view/index/id/1
or
/administrador/pages/view/index/page/1
If you want to remove the index part then set up routes like
$routeAdmin = new Zend_Controller_Router_Route(
// Remove the action from here and explicitly set the controller
'administrador/pages/:pg',
array(
'module' => 'administrador',
'controller' => 'pages',
// Then set the default action here
'action' => 'index',
'pg' => 0
),
array(
'pg' => '\d+'
)
);
$router->addRoute('administradorpages', $routeAdmin);
What your asking for basically results in a lot of guess work and therefore risk of producing unexpected results.
Have a look at dynamic segments in routes. It is not exactly what you want, but it might be helpful in your case.