PHP7 で PSR-7 と Middleware を使うマイクロフレームワークを書いてみた
コードはこちら。https://github.com/brtriver/karen
[追記]
この記事に書いてあるコードからさらに改良加えてApplicationレイヤーを作りました(v0.2)
詳しくはこっちの記事を参照をば
http://d.hatena.ne.jp/brtRiver/20160106/karen_framework
この記事の時点のコード(v0.1)を見たい場合は
https://github.com/brtriver/karen/tree/v0.1.3
からどうぞ。
なにこれ?
PSR-7が用意されてからコンポーネントを色々好きなのを選択できる時代が来つつあります。
たとえばzend-expressiveとか。
ただフレームワークががんばってこれらを抽象化しようとしてるのですが、もっとシンプルでもいいなぁと。
というわけで、コンポーネントをむき出しにして、ざぁーっと書いたらどうなるかをヤッてみたかったので書いただけという。
結果こんな感じに
https://github.com/brtriver/karen/blob/master/web/index.php
試してみたい人は
php -r "eval('?>'.file_get_contents('https://getcomposer.org/installer'));" php composer.phar create-project brtriver/karen ./<パス> cd <パス> make server // http://localhost:8888/hello/karen_girls
で。
Karenでやったこと
「こういう処理をやる」ということをラベル(コメント)ブロック付けた
スコープが閉じられるわけじゃないです。あくまでもラベル。
ただインラインコメントを残すよりもわかりやすかなと。
<?php container: { $c = new Container(); .... } middleware: { $relayBuilder = new RelayBuilder(); ... }
さすがにサービスコンテナ無いと辛そう
コンテナは Container Interop というのも用意されてたりしますが、まだ公式というほどでもないのと、好きなの使えばいいじゃんということで使い慣れた Pimpleを選択。
ルーティングは Aura.Router
ルーティングはクロージャーが定義できればいいので、使ったことがある Aura.Routerで
<?php ... $map->get('hello', '/hello/{name}', function($args, $controller) { $name = $args['name']?? 'karen'; return $controller->render('Hello, ' . $name); })->tokens(['name' => '.*']);
PHP7だと issetじゃなくて "??" 使えるの便利ですね。
KarenではControllerクラスを用意して、便利関数やRequest, Responseオブジェクトにクロージャーからアクセス出来るようにしてあります。
コントローラークラスの拡張を無名クラスでもできるように
必要があればControllerをextendsした専用のコントローラーを用意すればいいのですが、PHP7で無名クラス使えるので無名クラスでControllerを拡張できるようにしてみました。
たとえば通常は
<?php ... $c['controller'] = function($c) { return new Controller($c['request'], $['response']); };
と、コントローラーの用意しますが、
Templatable トレイトを利用できるようにしたControllerを用意したい場合は
<?php ... $c['controller'] = function($c) { $controller = new class($c['request'], $c['response']) extends Controller{ use Templatable; }; $controller->setTemplate($c['template']); return $controller; };
書いてみてどうだったの?
- まだもう少しコードを整理して書くつもり。
- コード書くのが疲れたので、感想はいつかのLTのネタとして。