Laravel備忘録:更新エラー時の処理(バリデーション)
更新時のエラー処理でハマりました。
更新時にかっこよくエラーの理由を表記してくれる機能『バリデーション』Laravelではかなり便利に作られていて簡単に利用できる...はずでした。
Laravel初心者の私がドはまりし解決にまる1日を要した理由を結果から分析し紐解いてみます。
バリデーターはどこに書くか
ドはまりの理由はこれです。
テキストとしている書籍を読み、不足情報をネットで補いと作業しているからこそ上記のポイントで正解を見失いました。
解決した後に情報を整理してみると、validationを記載する箇所は様々であることがよくわかります。
また、それぞれに理由もあり素人の混乱するポイントとなっていると思います。
具体的には以下の2点への記載方法レクチャーが多かったです。
- コントローラーへの記載
- app\Http\Requestへの記載
書籍の記入例は app\Http\Request の例が多い
理由はMVCモデルとしての思想なのだと思います。書籍が解説する訳ですから、きっとセオリーなのだと思います。
私がドはまりした原因の1つなので思う所もありますが...。
利点は2つです。
- コントローラー内が汚れない
- 別のControllerでも呼び出せる(流用出来る)
ちなみに、なぜ私がハマったか。それはテーブルの読込をModelで行っていたからです。
コントローラーにテーブル読込を記載した場合、useに設定を書き込めば素直にバリデータを持ってきます。
やり方はあるのでしょうが、私はテーブルの読込をModelに持って行った場合エラーで動かせませんでした。
ネット上はコントローラーへのバリデータ記入が多い
ネット上の情報はコントローラーへの記載が多いように思います。
確かにどこでどのバリデータを使う等細かい動作を調整しようと考えた場合、非常に扱い易いです。
- 書いていて理解しやすい
- どのパーツで動作するか判り易い
- JOINされたテーブルへの適用も簡単
コントローラーへの記載は同じ内容を何度も書く事にもなるので「MVCモデルの設計思想にあっているのか」と疑問に思う所もあります。
でもネット情報でこの記載方法が多いと言う事はそれだけ実践では使いやすいと言う事なのだと認識しています。
Modelへのバリデータ記載について
書籍ではコントローラーで様々な処理をして『こういった機能をModelに記載するとスッキリするんだよ』と話を進めるテキストが多いです。その為、validationはコントローラーで様々な動作をさせる時に登場し、その後のモデルへの移行ではあまり触れられません。
私がハマった理由はそんな事が原因でした。
テーブル取得をModelに移した時、そこへバリデータを書き加えると思います。その際、エラー処理を記載してしまえばモデルとリクエスト2か所に記載するようなことはなくなります。
私の書いた例です。
app\Models\Contaft.php
<?php
namespace app\Models;
use Illuminate\Database\Eloquent\Model;
class Contact extends Model
{
protected $guarded =array('id');
public static $rules = array(
'name' => 'required',
'email' => 'email',
'subject' => 'required',
'content' => 'required'
);
private $errors;
public function validate($data)
{
$v = Validator::make($data, $this->rules);
if ($v->fails())
{
$this->errors = $v->errors();
return false;
}
return true;
}
public function errors()
{
return $this->errors;
}
}
これをコントローラーにuse登録します。
namespace app\Http\Controllers; use Illuminate\Http\Request; use app\Models\Contact;
まとめ
あくまでもLaravelの入り口を覗いている現檀家での感想です。
- バリデーションの設定方法は様々ある。
- シングルテーブルのコントロールならModelへの記載がベスト?
- JOINTを利用する場合はコントローラーで扱うしかなさそう
どこに何があるか明確になるため、MVCモデルはプログラムの見直しがしやすいと感じています。
その為、改善しやすく大人数での開発にも耐える設計指標となているのでしょう。
ただ、一人で作ってる私には多少窮屈な感じが否めないのも事実。
何事も一長一短ですね。



このやり方は素晴らしいと思いました。
導入したいと思います。
しかし以下の問題点が発生しました。
私は、コントローラ層、サービス層、モデル層に分けています。
コントローラ層→サービス層→モデル層の順に層を見ています
なので、コントローラ層はモデル層を見ないことになっています。そうするとモデル層でvalidate()やerrors()を実装することになりますが、その結果をコントローラーへ渡すにはどのようにしたらよいでしょうか?
throwで渡すことを考えましたが、何かいい方法はありますでしょうか?
返信をよろしくお願いいたします。
すみません、スパムフォルダに自動投入されており気づくのが遅くなてしまいました。
サイト拝見させていただきました所、すでに自己解決されたようですね。
コメントを頂いたその日にバリデーションの記事が上がっている事を確認させていただきました。
Modelsに記載したバリデータから回答を得る方法は沢山あると思います。
その一つが、use で利用宣言をしてしまう事です。
Controller層はModel層を見ないと言う事なので、このような使い方はしたくないと言う事なのだと思いますが...。
それぞれの層でどこまで行いどの結果をreturnするのか、そこを詰めていくとプログラムにとっての最適解が得られるのではないでしょうか。
同じシステム人、頑張りましょう!