kaz_29@はてな

2010-02-18

独自namedパラメータを使って逆ルーティング

| 09:32 | 独自namedパラメータを使って逆ルーティングを含むブックマーク

結構な忙しさなのですが、id:cakephperさんのTweetをみて妙に納得してしまったので、昨日はまってた事をまとめました。

CakePHP 1.2.5で開発中です。

namedパラメータはなかなかに便利なのですが、独自のnamedパラメータを使っているURLの逆ルーティングではまったのでちょっと調べてみました。

通常の以下の様なルーティングであれば、独自のnamedパラメータも問題なく使えます。

<?php
Router::connect('/:controller/:action/*');

$url = Router::url(array('controller' => 'posts', 'action' => 'index', 'mode' => 'test')) ;
// 正しく変換できます
// $url = "/posts/index/mode:test"

ところがprefix routingを使ったりすると状況が変わります。例えば、以下の様に携帯対応のためにprefix routingとURLセッションキーを埋め込むような場合ですね。

<?php
Router::connect('/m/:session/:controller/:action/*', 
  array('prefix' => 'mobile', 'mobile' => true), 
  array('session' => '[a-zA-Z0-9]{32}')
);

$url = Router::url(array('controller' => 'posts', 'action' => 'index', 
  'mobile' => true, 'page' => 1, 'session' => '11111111112222222222333333333344')) ;
// page等のCakePHPで標準的に使われているnamedパラメータは問題なし
// $url = "/m/11111111112222222222333333333344/posts/view/page:1"

$url = Router::url(array('controller' => 'posts', 'action' => 'index', 
  'mobile' => true, 'mode' => 'test', 'session' => '11111111112222222222333333333344')) ;
// 独自のnamedパラメータを使うとこんな感じになってしまいます
// $url = "/posts/view/mobile:1/mode:test/session:11111111112222222222333333333344"

色々と調べた結果、namedパラメータとして使用する変数名を登録することができるようです。

Routerクラスに定義されている、connectNamedを使うことで使用可能なnamedパラメータをカスタマイズすることができます。

例えば上記の例の場合には、以下のように指定すると正常に変換できるようになります。

<?php
// 'default'=>true を指定しないとCakePHP標準のnamedパラメータを上書きしてしまうので注意!
Router::connectNamed(array('mode'), array('default'=>true)) ;

connectNamedメソッドのコメントを見ると適用するコントローラやアクションを指定出来そうなのですが、私が試した範囲では制限をかけられませんでした。(アプリすべてのコントローラに適用されます)

追いかけきれていないので、時間ができたらもう少し調べてみたいと思います。

参考

  • ルーティングの設定に失敗するとハマる事がおおいので、しっかりテストも書きましょう!ということで、ルーティングのテストについては以下の新原さんの記事がとても参考になります!

hiromi2424hiromi2424 2010/02/23 03:55 1.3になってreverse routingやprefix routingが改良されたので、期待したほうがいいかもです。(stableじゃないから、今すぐには実務で使えないでしょうけど・・・

kaz_29kaz_29 2010/02/23 11:03 ですね!個人的に作っているプラグインは、1.3で開発をしてるのですが結構細々と改良されているので期待しています!

トラックバック - http://d.hatena.ne.jp/kaz_29/20100218/1266453139