Building Advance Blog on Laravel 5.5 with TDD mode #4 User can submit comment
Tags: webdev, laravel5, laravel, phpdevelopers
Published: 2017-11-26 13:03:32

---
title: "Building Advance Blog on Laravel 5.5 with TDD mode #4 User can submit comment"
published: true
tags: web-development,laravel-5,laravel,php-developers
canonical_url: https://medium.com/lordofdev/building-advance-blog-on-laravel-5-5-with-tdd-mode-4-user-can-submit-comment-da93b528c86
---

![](https://cdn-images-1.medium.com/max/1024/1*WoNi1iErxX_TEF3oBY3NRQ.png)

in the previous episode, we display comment by creating test first   
again in this episode starting with a&nbsp;feature

User can submit&nbsp;comment

if you follow this first post I don’t use User in test case because require authentication state

but now we don’t allow guest or anonymous submit a&nbsp;comment

#### A Post can add&nbsp;comment

first, we test in small scale with deep down to unit level generate unit test file name PostTest with&nbsp;artisan

php artisan make:test PostTest&nbsp;--unit

open this file and fill user story&nbsp;first

```
public function test_a_post_can_add_a_comments()
    {
          //Giving a Post
         // Add a commemnt
        // Then post should have a comment

}
```

next fill in&nbsp;blank

```
public function test_a_post_can_add_a_comments()
    {
        //Giving a Post
        $post = factory('App\Post')->create();
        // Add a comemnt
        $post->storeComment([
                'body'=>'Testing',
                'user_id'=>1
        ]);
        // Then post should have comment
        $this->assertCount(1,$post->comment);
    }
```

try test

p filter tests/Unit/PostTest.php

result

![](https://cdn-images-1.medium.com/max/897/1*iTDA90xpO_D6XsVAagswcQ.png)

ok this make&nbsp;sense

open Comment&nbsp;Model

![](https://cdn-images-1.medium.com/max/542/1*BXpEMMCC-j4r9Wr6Jk9n1Q.png)

fill $guarded

and run single test&nbsp;again

![](https://cdn-images-1.medium.com/max/728/1*C6QQgmk6FhvzHerrV7tP5Q.png)

we got&nbsp;green

### Submit Comment Test Feature&nbsp;Test

next we up level to create comment but in big scale&nbsp;with

1. create route for connect to&nbsp;endpoint
2. create and save comment object to&nbsp;DB
3. check comment are exist in show&nbsp;page

The only user can submit a comment is a feature test because it’s work with other&nbsp;feature.

Doesn’t isolate them self from display&nbsp;name.

Open terminal php artisan make:test SubmitComment

Let’s generate user&nbsp;story

```
public function test_user_can_submit_comment(){

// Given a Guest
          // make guest to Authenticate user 
         // And Post is exist
        // And Giving comment object 
       // When the user submit comment to the post
      // Then their should see comment

}
```

next fill in the&nbsp;blank

```
public function test_user_can_submit_comment(){
         // Given a Guest
          $guest = factory('App\User')->create();
          // create Authenticate user 
         $user = $this->be($guest);
         // And Post is exist
         $post = factory('App\Post')->create();
         // And Giving comment object 
         $comment = factory('App\Comment')->make();
         // When the user submit comment to the post
    $this->post('/blog/'.$post->id.'/comment',$comment->toArray());
         // Then their should see comment
         $this->get('/blog/'.$post->id)->assertSee($comment->body);

}
```
> Note:: You’ve see when create comment why I use make instead of create because make only create object doesn’t create DB record and we use object create real record in next line [for more reference](https://laravel.com/docs/5.5/database-testing#using-factories)

now we got a map let’s&nbsp;follow

first this should&nbsp;red

![](https://cdn-images-1.medium.com/max/931/1*5My5SYDrGy3_oCELlTCVMw.png)

### Create route&nbsp;first

```
Route::post('/blog/{post}/comment','CommentController@store');
```

next create endpoint&nbsp;, in CommentController create store method for call storeCommment

```
use Illuminate\Http\Request;
use App\Post;
class CommentController extends Controller
{
      public function store(Post $post,Request $request){
            $post->storeComment([
                
                 'body'=>$request->get('body'),
                 'user_id'=> auth()->id()
            ]);
      }
}
```

save and test&nbsp;again

![](https://cdn-images-1.medium.com/max/737/1*oqJw4YVln1lrhA0GxxFdiQ.png)

Gotcha&nbsp;,we got&nbsp;green

but some detail I’ve&nbsp;fixit

#### An authenticate user only can submit&nbsp;comment

we need to block a guest that try to submit comment with add auth middleware

in CommentController

```
public function _construct(){
           $this->middleware('auth');
       }
```

and for making sure we add a test for check&nbsp;this

![](https://cdn-images-1.medium.com/max/779/1*QKi2hFvzZbrCj-hyFGVpZg.png)

comment $this-\>be and change $user to unauthenticated user

try p

![](https://cdn-images-1.medium.com/max/1024/1*rOLVtJTij0ekBgpeyn9DmA.png)

ok that’s work let’s me&nbsp;explain

when user doesn’t authenticate and post request to end point it’s doens’t&nbsp;work

for next step in our test it’s call get for orignal post that add&nbsp;comment

we expect to see comment that we create before but that doesn’t&nbsp;create

and try uncomment

![](https://cdn-images-1.medium.com/max/654/1*0QNlBa7AeApZFtpkK0jwjA.png)

save and test&nbsp;again

![](https://cdn-images-1.medium.com/max/665/1*taS2QfugKarabbvNACgJeg.png)

ok let’s separate function to check if a guest can’t submit a&nbsp;comment

grab code from before test but remove $user = $this-\>be($guest);

```
function test_guest_can_not_submit_comment(){
        // Given a Guest
          $guest = factory('App\User')->create();
         // And Post is exist
         $post = factory('App\Post')->create();
         // And Giving comment object 
         $comment = factory('App\Comment')->make();
         // When the user submit comment to the post
          $this->post('/blog/'.$post->id.'/comment',$comment->toArray());
         // Then their should see comment
    $this->get('/blog/'.$post->id)->assertSee($comment->body);
     
    }
```

test again

![](https://cdn-images-1.medium.com/max/1024/1*JXo_S_VfrGfpml91is1yoA.png)

should fail next make it&nbsp;green

```
function test_guest_can_not_submit_comment(){
        // Given a Guest
          $guest = factory('App\User')->create();
         // And Post is exist
         $post = factory('App\Post')->create();
         // And Giving comment object 
         $comment = factory('App\Comment')->make();
         // When the user submit comment to the post
          $this->post('/blog/'.$post->id.'/comment',$comment->toArray());
         // Then their should don't see comment
    $this->get('/blog/'.$post->id)->assertDontSee($comment->body);
     
    }
```

rerun test

![](https://cdn-images-1.medium.com/max/835/1*Ed8uLz-MyLO4ZW53Alxvcg.png)

it’s green

we completely work under the&nbsp;hood.

### Finish in&nbsp;frontend

now that’s time to add form for end of this&nbsp;episode

first I’ve give name to&nbsp;route

```
Route::post('/blog/{post}/comment','CommentController@store')->name('addcomment');
```

then openpost/show.blade.php

scroll to bottom&nbsp;page

copy code this&nbsp;below

```
@if (auth()->check())
             <div class="row">
                 <div class="col-md-8 col-md-offset-2">
                     <form method="POST" action="{{ route('addcomment',$post->id) }}">
                        {{ csrf_field() }}
 
                         <div class="form-group">
                             <textarea name="body" id="body" class="form-control" placeholder="Have something to say?" rows="5"></textarea>
                         </div>
                         
                         <button type="submit" class="btn btn-default">Post</button>
                    </form>
                 </div>
             </div>
         @else
             <p class="text-center">Please <a href="{{ route('login') }}">sign in</a> to comment in post.</p>
         @endif
```

and paste to this&nbsp;position

![](https://cdn-images-1.medium.com/max/1024/1*hFHhuRD8C-M3-F1bGv_4Jg.png)

save and next go to&nbsp;check

![](https://cdn-images-1.medium.com/max/839/1*hUu5TVUlspIemUoHG19OQA.png)

click on link for&nbsp;signin

![](https://cdn-images-1.medium.com/max/1024/1*WSSNFaGYPm1p44wIc1le1w.png)

after sign in go to some post and add&nbsp;this

![](https://cdn-images-1.medium.com/max/923/1*IFEwHsMWsOlp8yBJ_vb31g.png)

and submit You’ve redirect back to this&nbsp;page

![](https://cdn-images-1.medium.com/max/902/1*CglAZ0IvyCCZIjOSt6JmIQ.png)

ok it’s almost completely work&nbsp;fine

### bonus section

#### display post&nbsp;creator

we know comment&nbsp;creator

![](https://cdn-images-1.medium.com/max/866/1*c9OP_WbYPn_rNgJdV4562A.png)

but we don’t know who post&nbsp;creator

let’s display it with TDD way with write test&nbsp;first

open tests/Unit/PostTest.php

add function test\_post\_has\_a\_creator

```
function test_post_has_a_creator()
    {
        // Giving post 
        // expect found User who create post
    }
```

fill in&nbsp;blank

again

```
function test_post_has_a_creator()
    {
        // Giving post 
        $post = factory('App\Post')->create();
        // expect found User who create post
        $this->assertInstanceOf('App\User', $post->creator);
    }
```

let’s test&nbsp;again

![](https://cdn-images-1.medium.com/max/619/1*vZ9jHMantRnrJLUQZwyVSQ.png)

should fail

next we add relationship for Post&nbsp;model

![](https://cdn-images-1.medium.com/max/588/1*47klH1gUrJkHgzx2K6am5A.png)

run test&nbsp;again

![](https://cdn-images-1.medium.com/max/673/1*zf4Lno1xAJpg-BWXyTQnjw.png)

display in post add to single&nbsp;post

![](https://cdn-images-1.medium.com/max/803/1*w0eDMVBZIBQhouQ_cL69IQ.png)

save and&nbsp;refresh

![](https://cdn-images-1.medium.com/max/1024/1*KkYjUAuyRDfiyzrpbfj2jQ.png)

complete

before we end in this episode I’ve need tweak something

with add home&nbsp;menu

![](https://cdn-images-1.medium.com/max/797/1*kgTm3ccOzkfeD3H91mfRVw.png)

first I’ve add name to blog&nbsp;route

![](https://cdn-images-1.medium.com/max/1024/1*QrS2K8_hxn-wz39NOuHAPg.png)

save and&nbsp;refresh

![](https://cdn-images-1.medium.com/max/756/1*MC-O2GbFuL9t8Epe5Guxig.png)

got blog&nbsp;menu

hope your enjoy&nbsp;this

**if you like this please give me 50 claps and hit follow that encouragement to move&nbsp;forward**

**this** [**project Github commit**](https://github.com/krissnawat/advance-blog-in-laravel-5.5-in-tdd/commit/1523cb175b97dd7716c3af8b6743ad81d83c3b8e) **and you can star&nbsp;it**

* * *