How to test routes' middleware?

Viewed 1488

Let's say I have a group of routes which are protected by a middleware:

Route::group(['middleware' => 'verified'], function () {
    Route::get('/profile', 'ProfileController@show')->name('profile.show');
    Route::get('/settings', 'SettingsController@show')->name('settings.show');
});

How can I test that these routes are protected by verified middleware? If I write those tests, are they considered as feature tests or unit tests?

1 Answers

Middleware testing highly depends on the logic of the middleware itself and on the possible outcomes. Let's take the verified middleware you cited as an example:

We expect the user to be redirected (302) to the "Verify your email" page if it has not verified his email (the email_verified_at attribute is null), otherwise we expect a normal response (200).

How can we simulate a user accessing our page? With the actingAs method. From the docs:

The actingAs helper method provides a simple way to authenticate a given user as the current user.

So our code will look something like this:

use App\User;

class ExampleTest extends TestCase
{
    public function testAccessWithoutVerification()
    {
        // Create a dummy user
        $user = factory(User::class)->create();

        // Try to access the page
        $response = $this->actingAs($user)
                         ->get('/the-page-we-want-to-test');

        // Assert the expected response status
        $response->assertStatus(302);
    }

    public function testAccessWithVerification()
    {
        // Create a dummy user, but this time we set the email_verified_at
        $user = factory(User::class)->create([
            'email_verified_at' => \Carbon\Carbon::now(),
        ]);

        // Try to access the page
        $response = $this->actingAs($user)
                         ->get('/the-page-we-want-to-test');

        // Assert the expected response status
        $response->assertStatus(200);
    }

}

The docs have an entire page dedicated to HTTP tests, check it out.

Related