前提・実現したいこと
ここに質問の内容を詳しく書いてください。
Laravelで商品(product)にコメント(comment)する機能を作っています。
ユーザーはその商品に対してコメントできるのですが、重複させないようにバリデーションをかけたいです。
■■な機能を実装中に以下のエラーメッセージが発生しました。
exists()のところにuser_idとproduct_idが存在するときは「すでにコメントは投稿済みです」とエラーメッセージを出したいです。
発生している問題・エラーメッセージ
バリデーションのときに、product_idがないよとバリデーションのエラ-メッセージに出ています。
product idは必須です。
該当のソースコード
CommentController
1<?php 2 3namespace App\Http\Controllers; 4 5use App\Comment; 6use App\Product; 7use App\Rules; 8use Illuminate\Support\Facades\Auth; 9use App\Http\Requests\CommentRequest; 10 11use Illuminate\Http\Request; 12 13class CommentsController extends Controller 14{ 15 public function new($p_id) 16 { 17 18 $product = Product::where('id', $p_id)->first(); 19 20 if(!Auth::check()) { 21 return redirect()->route('login'); 22 } 23 24 if(Auth::id() === $product->user_id) { 25 return redirect()->route('products.show', ['id' => $product->id]); 26 } 27 28 29 30 return view('comments.new', [ 31 'product' => $product 32 ]); 33 } 34 35 public function create(CommentRequest $request, $id) 36 { 37 $product = Product::find($id); 38 $request->validate([ 39 'product_id' => [ 40 'required', 41 'exists:products,id', 42 function($attribute, $value, $fail) use($request) { 43 // ログインしてるかチェック 44 if(!auth()->check()) { 45 46 $fail('レビューするにはログインしてください。'); 47 return; 48 49 } 50 $exists = Comment::where('user_id', $request->user()->id) 51 ->where('product_id', $product) 52 ->exists(); 53 54 if($exists) { 55 $fail('すでにコメントは投稿済みです。'); 56 return; 57 } 58 } 59 ], 60 ]); 61 62 $product->comments()->create([ 63 'title' => $request->title, 64 'star' => $request->star, 65 'body' => $request->body, 66 'user_id' => $request->user()->id, 67 68 ]); 69 70 71 return redirect()->route('products.show', [ 72 'id' => $product->id, 73 ]); 74 } 75} 76
CommentRequest
1<?php 2 3namespace App\Http\Controllers; 4 5use App\Comment; 6use App\Product; 7use App\Rules; 8use Illuminate\Support\Facades\Auth; 9use App\Http\Requests\CommentRequest; 10 11use Illuminate\Http\Request; 12 13class CommentsController extends Controller 14{ 15 public function new($p_id) 16 { 17 18 $product = Product::where('id', $p_id)->first(); 19 20 if(!Auth::check()) { 21 return redirect()->route('login'); 22 } 23 24 if(Auth::id() === $product->user_id) { 25 return redirect()->route('products.show', ['id' => $product->id]); 26 } 27 28 29 30 return view('comments.new', [ 31 'product' => $product 32 ]); 33 } 34 35 public function create(CommentRequest $request, $id) 36 { 37 $product = Product::find($id); 38 $request->validate([ 39 'product_id' => [ 40 'required', 41 'exists:products,id', 42 function($attribute, $value, $fail) use($request) { 43 // ログインしてるかチェック 44 if(!auth()->check()) { 45 46 $fail('レビューするにはログインしてください。'); 47 return; 48 49 } 50 $exists = Comment::where('user_id', $request->user()->id) 51 ->where('product_id', $product) 52 ->exists(); 53 54 if($exists) { 55 $fail('すでにコメントは投稿済みです。'); 56 return; 57 } 58 } 59 ], 60 ]); 61 62 $product->comments()->create([ 63 'title' => $request->title, 64 'star' => $request->star, 65 'body' => $request->body, 66 'user_id' => $request->user()->id, 67 68 ]); 69 70 71 return redirect()->route('products.show', [ 72 'id' => $product->id, 73 ]); 74 } 75} 76
試したこと
まず、バリデーションなしで、post送信をしたら、ちゃんとDBに登録され、product_idは入っていました。
しかし、バリデーションありの時では、$request->product_id送信があるにも関わらず「product_idがない」とエラーが出ています。
バリデーションの書く場所が間違っているのかと?
リレーションで紐づけをしているのに、バリデーションの時ではproduct_idが取得できなくて困っています。
補足情報(FW/ツールのバージョンなど)
Laravel6
php 7.4
Mysql
Homestead
vagrant
ここのサイトを参考に作っています。
Laravelでレビュー機能(星&コメント)をつくる
回答1件
あなたの回答
tips
プレビュー
バッドをするには、ログインかつ
こちらの条件を満たす必要があります。