CakePHP3を触ってみました 〜せがれをいじるよりroutesをいじろう〜

結局せがれいじりってどんなゲームなんだ?

おまとめ三行

せがれいじりも悪くはないのですが
あまり複雑なことはやりません
ラクダさんの出番が必要になる

せがれいじりも悪くはないのですが、CakePHP3になってURLの設定に関するところが前より簡単になったような気がするので、今日はそっちをいじることにしましょう。

あまり複雑なことはやりません。ちょっとURLに変化をつけてみようっていう、その程度。主にプレフィックスを使った話です。



CakePHP2でプレフィックスを使う

例えば、管理画面のURLを、全て「/admin/***」みたいな感じにしようと思った場合。

CakePHP2だと、まずcore.phpの中でプレフィックスに関する設定が必要になります。

Configure::write('Routing.prefixes', array('admin'));

これでプレフィックスが使えるようになります。

そんでもって、コントローラーやビューも、管理画面とフロント画面で分けたい場合。

例えば、「/users/index」ってURLと「/admin/users/index」っていう二つのURLを作成したいとしましょう。

フォルダ構成はこんな感じ。

/app
  ├ /Controller
  ├   ├ UsersController.php
  ├   └ /Admin
  ├       └ UsersController.php
  └ /View
      ├ /Users
      ├   └ index.ctp
      └ /Admin
          └ /Users
              └ admin_index.ctp

コントローラーにもビューにも、Adminというフォルダを作って、管理画面用のコントローラーやビューはそっちに書くとする。

この場合、bootstrap.phpで、管理画面の方のURLにアクセスした場合は、Adminフォルダの中を見に行くような設定を書いとく必要がある。

if(!empty($_SERVER['REQUEST_URI']) && preg_match('/admin/i', $_SERVER['REQUEST_URI'])) {
  App::build(array(
    'Controller' => array(
      ROOT.DS.APP_DIR.DS.'Controller'.DS.'Admin'.DS,
    ),
    'View' => array(
      ROOT.DS.APP_DIR.DS.'View'.DS.'Admin'.DS, 
    ),
  ));
}

正直、この書き方がベストかは分からないんですが、URLに「/admin/」って文字が含まれてたら管理画面の方のURLだって思うことにして、Adminフォルダの中を見るようにしています。

フロント画面と管理画面で同じ名前のコントローラーやビューを使わないなら、別にこの設定は必要ないです。ただ、上記のように同じUsersController.phpを作るみたいなことがあるのなら、分けとかないとCakeさんが適切にファイルを読み込んでくれない。

もちろん、一つのコントローラーの中でフロント画面と管理画面の両方のメソッドを書いちゃっても良いんですけどね。

//UsersController.php
class UsersController extends AppController {
  //フロント画面
  public function index() {}

  //管理画面
  public function admin_index() {}
}

プレフィックスを使う場合、メソッドやビューのテンプレートファイル名にプレフィックス名をつける必要があります。アンダーバーでつなぐ感じ。メソッド名が「admin_index」なら、テンプレートも「admin_index.ctp」となります。

こんな風に、メソッド名が被ることはないので、同じコントローラーやビューフォルダでも管理はできるんですが、僕の場合は分けて管理することが多いです。何でかっていうと、AppControllerを二つに分けたいからです。フロント画面と管理画面、それぞれにFrontAppConroller.phpとかAdminAppController.phpみたいなファイルを作って、それを継承するような作りにすることが多いので、フロント画面と管理画面でコントローラーやビューを完全に分けた方が楽なのです。

その辺は好みとか仕様次第だと思います。



CakePHP3でプレフィックスを使う

じゃあ、これと同じことをCakePHP3でやってみたいと思います。

3の場合、プレフィックスの設定は、core.phpではなく、routes.phpに書きます。

Router::prefix('admin', function ($routes) {
  $routes->fallbacks('DashedRoute');
});

これでオーケーです。先ほど同様、「/admin/***」というURLが使えるようになります。

3の方は、bootstrap.phpにフォルダ構成用の記述は必要ありません。これだけ書いとけば、自動的にAdminフォルダの方を見に行ってくれるようになります。こりゃあ楽で良いっすね。

ついでに、admin_indexみたいに、メソッド名にやテンプレートファイルにプレフィックスをつける必要もないです。

/app
  ├ /Controller
  ├   ├ UsersController.php
  ├   └ /Admin
  ├       └ UsersController.php
  └ /View
      ├ /Users
      ├  └ index.ctp
      └ /Admin
          └ /Users
              └ index.ctp

これで良いです。逆に言うと、メソッド名が被っちゃうことになるから、一つのファイルで管理することはできなくなったっぽいですね。

僕としては今まで通りだから、文字数が減った分だけ楽になったなぁっていう印象なのですが。



トップページに特定のページを設定してみる

例えば「http://hogehoge.jp」っていうサイトで、トップページにアクセスしたときに、UsersController.phpのindexページが表示されて欲しいとする。

CakePHP2の場合。

Router::connect('/', array('controller' => 'users', 'action' => 'index'));

routes.phpに、このような設定を書いとけば、「http://hogehoge.jp」と「http://hogehoge.jp/users/index」で同じページが表示されます。

じゃ、次にCakePHP3。

Router::scope('/', function ($routes) {
  $routes->connect('/', ['controller' => 'Users', 'action' => 'index']);
}

まあ、ほとんど一緒ですね。

プレフィックスを使えば、管理画面のトップページ(http://hogehoge.jp/admin)にも同じような割り当て方ができます。

//CakePHP2
Router::connect('/admin', array('controller' => 'users', 'action' => 'index', 'prefix' => 'admin'));

//CakePHP3
Router::scope('/', function ($routes) {
  $routes->connect('/admin', ['controller' => 'Users', 'action' => 'index', 'prefix' => 'admin']);
}

CakePHP3の場合、こんな書き方もできます。

Router::scope('/admin', function ($routes) {
  $routes->connect('/', ['controller' => 'Users', 'action' => 'index', 'prefix' => 'admin']);
}

結果は一緒です。「http://hogehoge.jp/admin」と「http://hogehoge.jp/admin/users/index」で同じページが表示されます。



アンダーバーつきURLについて

CakePHP3になってから、アンダーバーつきのURLは、アクションでキャメルケースするようになりました。

どういうことかってーと、例えば「http://hogehoge.jp/users/add_user」みたいなURLがあったとします。usersコントローラーのadd_userアクションが呼ばれると思って下さい。

この時、CakepHP2系と3系では、コントローラーの書き方がびみょ〜に違う。ビューは一緒。

//CakePHP2
class UsersController extends AppController {
  //URLと同じアンダーバーつき
  public function add_user() {}
}

//CakePHP3
class UsersController extends AppController {
  //キャメルケースする
  public function addUser() {}
}

テンプレートファイルはどちらも「add_user.ctp」で良いんですが、コントローラのアクションは、3の方はアンダーバーつきで書くとエラーになります。ラクダさんの出番が必要になる。






こんなとこでしょうか。

routes.phpでちょちょっと設定するだけで良くなったのが、個人的には気に入ってます。

設定が簡単になったってことは、それだけコードを書く時間も短縮されるわけで、つまり空き時間が増えるわけで、時間が空いた分だけ、今まで以上にせがれいじりに没頭できるってことになるじゃないですか!

いや、まあ、別にそういう理由で気に入ってるわけでは、ないですけど……。



その他のCakePHP3を触ってみましたの記事はこちら
まとめという名の箸休め

まだコメントはいただけてないみたい……
もしかしたら何か関連しているかも?