CakePHP – Как сделать обратную маршрутизацию с помощью пули?

Я использую CakePHP 1.3. У меня есть модель продукта. в таблице DB среди других есть поля id и slug .

Если у меня есть продукт, который является id:37 и slug:My-Product-Title Я хочу, чтобы URL-адрес продукта был следующим:

Продукты / 37 / My-Product-Title

Вместо стандарта:

Продукты / Вид / 37

Я создал маршрут, который выглядит так:

 Router::connect( '/products/:id/:slug', array('controller' => 'products', 'action' => 'view'), array('pass' => array('id'), 'id' => '[0-9]+') ); 

Теперь я могу перейти на http://server/products/37/My-Product-Title и он доставит меня в нужное место.

Но как мне получить обратную маршрутизацию для автоматического создания правильного URL-адреса в $HtmlHelper->link ?

Когда я использую:

 echo $html->link( 'Product 37', array('controller'=>'products', 'action' => 'view', 37) ); 

Он по-прежнему выводит стандартный products/view/37 url.

Я не верю, что это можно сделать автоматически. Помощник – это просто «помощник», который строит ссылку из заданных параметров.

Поэтому самый простой способ – добавить еще один параметр в вашу ссылку:

 echo $html->link( 'Product 37', array('controller'=>'products', 'action' => 'view', 37, $slug) ); 

где $ slug – данные из поля slug.

Наверное, это может быть ваша идея, но вам очень нужно разбить шаблон MVC 🙂

Редактировать:

Повторяя ваш вопрос, я хорошо это понял. Посмотрите, как это сделать:

в вашем router.php добавьте следующее правило:

 Router::connect( '/product/*', array('controller' => 'products', 'action' => 'view') ); 

Обратите внимание, что это / product / *, а не / products / *

Ваша ссылка должна быть выполнена следующим образом:

 echo $html->link( 'Product 37', array('controller'=>'products', 'action' => 'view', 37, 'my-product-title') ); 

и ссылка будет выглядеть так:

 http://yourdomain.com/product/37/my-product-title 

Для меня твоя идея – плохая практика. Также я не думаю, что это хорошо с точки зрения SEO, перенаправляющей всегда пользователя.

Для маршрутизации:

 Router::connect( '/products/:id/:slug', array('controller' => 'products', 'action' => 'view'), array('pass' => array('id'), 'id' => '[0-9]+') ); 

Ваши ссылки должны выглядеть так:

 echo $html->link( 'Product 37', array('controller'=>'products', 'action' => 'view', 'id' => 37, 'slug' => 'my-product-title') ); 

Вы должны добавить дополнительный (ключ => значение) в свой массив для каждого: param в вашей маршрутизации. Тогда магия будет работать

Вы должны посмотреть следующее сообщение о пользовательских классах маршрутов.

Данные пробки не обязательно должны быть связаны с базой данных – поле является поддельным полем, используемым для упрощения логики и поиска. Это решение позволяет вам сбрасывать маршрутные пули, не требуя поля для пули в таблице моделей.

http://42pixels.com/blog/slugs-ugly-bugs-pretty-urls

Я не уверен, насколько это плохо, но со следующим кодом в ProductController:

 function view($id) { if( isset($_SERVER) && stristr($_SERVER["REQUEST_URI"],'view/') ) { $this->Product->id = $id; $slug = $this->Product->field('slug'); $this->redirect($id.'/'.$slug); } $data = $this->Product->find('first', array('conditions' => array('Product.id' => $id))); $this->set("data", $data); } 

Если страница обращается через /view/id она автоматически перенаправляет их на текущую страницу с помощью /id/slug

Теперь я могу использовать схему ссылок по умолчанию:

 echo $html->link( 'Product 37', array('controller'=>'products', 'action' => 'view', 37) ); 

и они будут перенаправлены на правильный URL.

Единственная проблема заключается в том, что я не уверен, насколько плохо, чтобы перенаправление происходило каждый раз, когда пользователь посещает страницу продукта?