Create a Laravel 8 Blog - Part 5: Comment CRUD

Overview

At the end of this you'll have a blog post view like this Single blog post example

New post form

  1. Make a new folder for the blade files
mkdir resources/views/blog/comments/
  1. Add new CommentController
./vendor/bin/sail artisan make:controller CommentController
  1. Add a save method + path (/admin/blog/comment) to the route file.

Add the route inside the /blog prefix group.

# routes/web.php Route::post('/comment', 'App\Http\Controllers\CommentController@save');
# app/Http/Controllers/CommentController.php <?php namespace App\Http\Controllers; use Illuminate\Http\Request; use App\Models\Comment; class CommentController extends Controller { public function save(Request $request) { $comment = new Comment(); $comment->comment = $request->get('comment'); $comment->user_id = $request->user()->id; $comment->post_id = $request->get('post_id'); $comment->save(); return redirect() ->back(); } }

See the commit

  1. Add the form to create a comment and add it to the single post view
# resources/views/blog/comments/create.blade.php <form action="/admin/blog/comment" method="post" class="container"> <input type="hidden" name="_token" value="{{ csrf_token() }}" /> <input type="hidden" name="post_id" value={{ $post->id }} /> <div class="form-group"> <label for="comment">Comment</label> <textarea name="comment" class="form-control"></textarea> </div> <input type="submit" name="submit" class="btn btn-success" value="Comment" /> </form>

Add the include to the blog post blade file so it displays the comment form.

# resources/views/blog/posts/single.blade.php <h3>Comments</h3> @include('blog.comments.create')

See the commit

  1. Display comments on a post

We'll update the PostController to include the comments as view data.

$comments = $post->comments()->get(); return view('blog.posts.single', ['post' => $post, 'comments' => $comments]);

Add a new blade file for an individual comment

# resources/views/blog/comments/single.blade.php <li> <div> <h4>{{ $comment->author()->first()->name }} <small>({{ date('Y-m-d', strtotime($comment->created_at)) }})</small></h4> <p>{{ $comment->comment }}</p> </div> </li>

Update the single post blade file to loop the comments and render them.

# resources/views/blog/posts/single.blade.php @extends('layouts.app') @section('content') <div class="container"> <h1>{{ $post->title }}</h1> <p>{{ $post->body }}</p> <h3>Comments</h3> @include('blog.comments.create') <br /><br /> <ul class="comment-list"> @foreach ($comments as $comment) @include('blog.comments.single') @endforeach </ul> </div> @stop

See the commit

  1. Add a way to delete a comment for admins only

Update the single post blade file to include a delete button.

# resources/views/blog/comments/single.blade.php @auth <form action="/admin/blog/comment/{{ $comment->id }}" method="post"> <input type="hidden" name="_token" value="{{ csrf_token() }}" /> <input type="hidden" name="_method" value="DELETE"> <input type="submit" name="delete" class="btn btn-danger" value="Delete" /> </form> @endauth

Add the route

# routes/web.php Route::delete('/comment/{commentId}', 'App\Http\Controllers\CommentController@delete');

Update CommentController to support the new delete route.

# app/Http/Controllers/CommentController.php public function delete(Request $request, int $commentId) { $comment = Comment::where('id', $commentId)->first(); if ($request->has('delete')) { $comment->delete(); $message = 'Comment deleted!'; } return redirect()->back(); }

See the commit

Roundup

That's it for now. Part 6 will go through adding validation to ensure nothing breaks from user input.

Next: Validation

If you have any feedback for me, I'd love to hear it - corrections, alternative paths, you name it! Send me an email levi@levijackson.xyz