CakePHP3の機能の1つ、モデルのないフォームを実際の開発で何回か使うことがあったので、どんな機能なのかを掻い摘んで紹介しつつ、実際の利用シーンについて紹介する。検証したCakePHPのバージョンは3.6.13。
モデルのないフォームの特徴
モデルのないフォームは、DBに対象となるテーブルがなくてもTableClassにあるValidatorを使ったり、Migrationのようにテーブルのcolumnと同様の定義を行ってフォームからの入力値を検証することができる便利な機能だ。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 |
namespace App\Form; use Cake\Form\Form; use Cake\Form\Schema; use Cake\Validation\Validator; class ContactForm extends Form { protected function _buildSchema(Schema $schema) { return $schema->addField('name', 'string') ->addField('email', ['type' => 'string']) ->addField('body', ['type' => 'text']); } protected function _buildValidator(Validator $validator) { $validator->add('name', 'length', [ 'rule' => ['minLength', 10], 'message' => '名前は必須です' ])->add('email', 'format', [ 'rule' => 'email', 'message' => '有効なメールアドレスが要求されます', ]); return $validator; } protected function _execute(array $data) { // メールを送信する return true; } } |
公式ドキュメントより拝借するが、こんな風↑に書いて、
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 |
namespace App\Controller; use App\Controller\AppController; use App\Form\ContactForm; class ContactController extends AppController { public function index() { $contact = new ContactForm(); if ($this->request->is('post')) { if ($contact->execute($this->request->getData())) { $this->Flash->success('すぐにご連絡いたします。'); } else { $this->Flash->error('フォーム送信に問題がありました。'); } } $this->set('contact', $contact); } } |
こんな感じ↑でControllerから呼び出すことができる。なんと簡単だろうか。
execute()メソッドは、入力データをnewEntity()やpatchEntity()でデータ検証して保存するまでの一連の流れを再現可能なメソッドだと思ってもらえればOK。validate()メソッドを使えば、入力データを検証だけさせることも可能だ。もしValidationErrorがあれば、$contact->errors()でエラー内容を取得することもできる。
モデルのないフォームの使い所
いくつか候補がある。
- LP(ランディングページ)の入力フォーム
- お問い合わせフォーム
- API
の3つだ。
1.はLPに入力フォームがあるが、入力値はDBへ保存せずにメールで通知させるだけの処理等に最も効果がある。2.も1.と似たようなシチュエーションだ。
3.はAPIがコールされた際に受け取るkeyとvalueで構成された値をチェックしたいシーンが想定される。HTTPメソッドがGETで返却値が1つのテーブルから情報を返す場合にはFormよりもTableのValidatorを使ったほうが手っ取り早いかもしれないが、GETで返却値が複数テーブルから情報を返す時や、HTTPメソッドがPOST/PUT/DELETEで且つ複数テーブルのデータに追加/更新/削除をさせたい場合には威力を発揮する可能性がある。
また、入力フォームにDBへ保存する項目とそうでない項目がある時にも活用の余地がある。例えば入力フォームにユーザーに同意を得るためのチェックボックス(DBにはチェックされたかどうかは保存しない)が複数個あったりする時だ。他にも使い所はありそうな気がするので、実運用してみてまた何かアイデアを見つけたら随時ここの内容を更新していく予定。