DEV Community

Cover image for Laravel Dusk with Github Actions
Muhammad Adib Ahmad Roslan
Muhammad Adib Ahmad Roslan

Posted on

Laravel Dusk with Github Actions

Hello,

i was tasked to do Unit Testing for one of my projects, the test case that i was tasked with is :-

  • User can login and see Dashboard
  • User can login and see Developer Portal
  • User can login and see Administration Panel

basically the test is quite easy and straight-forward right?

so im off with installing Laravel Dusk since this kind of test involves with the actions of seeing the UI itself.

if you're not familiar with Laravel Dusk, Laravel Dusk is a official library that are supported by the Laravel itself.

Laravel Dusk provides an expressive, easy-to-use browser automation and testing API. By default, Dusk does not require you to install JDK or Selenium on your machine. Instead, Dusk uses a standalone ChromeDriver installation. However, you are free to utilize any other Selenium compatible driver you wish. - Laravel Dusk

So Without further ado,

The Preparation

Make sure that you have created the user factory, user seeder as well as enable user factory inside DatabaseSeeder.php file before starting this unit test. since its requires dummy user to test the test case.

Laravel Dusk Installation

installing Laravel Dusk is quite the breeze, just run this into the CLI of your project composer require --dev laravel/dusk after installing the packages you can then run php artisan dusk:install to install your laravel dusk.

Laravel Dusk Environment Configuration

By Default, when the laravel dusk environment configurations file .env.dusk is not exist, it will automatically use the .env as the environment configuration temporarily. in our case, we need to use a separate database which is called dusktest database and create the .env.dusk file onto your root project folder. Here's the sample of my .env.dusk

Important Make sure to generate the APP_KEY as well. run php artisan key:generate then copy the key from .env to .env.dusk

APP_NAME=dusk
APP_ENV=local
APP_KEY={your-key-here}
APP_DEBUG=true
APP_URL=http://127.0.0.1:8000

LOG_CHANNEL=stack
FLARE_KEY=

DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=dusktest
DB_USERNAME=root
DB_PASSWORD=

BROADCAST_DRIVER=log
CACHE_DRIVER=array
QUEUE_CONNECTION=sync
SESSION_DRIVER=file
SESSION_LIFETIME=120

REDIS_HOST=127.0.0.1
REDIS_PASSWORD=null
REDIS_PORT=6379

MAIL_MAILER=array
MAIL_HOST=smtp.mailtrap.io
MAIL_PORT=2525
MAIL_USERNAME=null
MAIL_PASSWORD=null
MAIL_ENCRYPTION=null
MAIL_FROM_NAME="${APP_NAME}"
MAIL_FROM_ADDRESS="no-reply@ksud.com"

AWS_ACCESS_KEY_ID=
AWS_SECRET_ACCESS_KEY=
AWS_DEFAULT_REGION=us-east-1
AWS_BUCKET=

PUSHER_APP_ID=
PUSHER_APP_KEY=
PUSHER_APP_SECRET=
PUSHER_APP_CLUSTER=mt1

MIX_PUSHER_APP_KEY="${PUSHER_APP_KEY}"
MIX_PUSHER_APP_CLUSTER="${PUSHER_APP_CLUSTER}"

Enter fullscreen mode Exit fullscreen mode

The Test Scripts

Run php artisan dusk:make CommonTest onto your CLI , it will created the Test File inside my-project/tests/Browser/CommonTest.php . After that we need to create the test case inside the test scripts . Here's the test scripts that i've created .

<?php

namespace Tests\Browser;

use App\Models\User;
use Illuminate\Foundation\Testing\DatabaseMigrations;
use Illuminate\Support\Facades\Artisan;
use Laravel\Dusk\Browser;
use Tests\DuskTestCase;

class CommonTest extends DuskTestCase
{
    use DatabaseMigrations;

    /**
     * Can Login and see Dashboard
     *
     * @return void
     */
    public function testCanLoginAndSeeDashboard()
    {
        //Seed dummy user data
        Artisan::call('db:seed');
        $user = User::first();
        $this->browse(function ($first) use ($user){
            $first->loginAs($user)
                  ->visit('/dashboard')
                  ->assertSee('Dashboard');
        });
    }

    /**
     * Can Login and see Developer Portal
     *
     * @return void
     */
    public function testCanLoginAndSeeDeveloperPortal()
    {
        //Seed dummy user data
        Artisan::call('db:seed');
        $user = User::first();
        $this->browse(function ($first) use ($user){
            $first->loginAs($user)
                  ->visit('/developer')
                  ->assertSee('Connective Exchange');
        });
    }

    /**
     * Can Login and see Administration Panel
     *
     * @return void
     */
    public function testCanLoginAndSeeAdministrationPanel()
    {
        //Seed dummy user data
        Artisan::call('db:seed');
        $user = User::first();
        $this->browse(function ($first) use ($user){
            $first->loginAs($user)
                  ->visit('/admin')
                  ->assertSee('Resources');
        });
    }
}

Enter fullscreen mode Exit fullscreen mode

Github Action Workflow

So basically if you're familiar with github actions , the github action workflow scripts should be inside my-project/.github/workflows/actions.yml you can rename the file as you desired.

# my-project/.github/workflows/actions.yml
name: Unit Test

on:
  push:
    branches: [develop]
  pull_request:
    branches: [master, develop]

jobs:
  PHPUnit:
    runs-on: ubuntu-latest
    services:
      mysql:
        image: mysql:8.0.21
        env:
          MYSQL_ALLOW_EMPTY_PASSWORD: yes
          MYSQL_DATABASE: dusktest
        ports:
          - 3306:3306
        options: --health-cmd="mysqladmin ping" --health-interval=10s --health-timeout=5s --health-retries=3

    steps:
      - uses: actions/checkout@v2
      - name: Configure Application
        run: bin/ci
      - name: Configure Laravel Dusk
        run: bin/ci-dusk
      - name: Execute Dusk tests via PHPUnit
        run: php artisan dusk

Enter fullscreen mode Exit fullscreen mode

you have to create some of this bash files to ensure the scripts working.

# my-project/bin/ci

#!/usr/bin/env bash

cp .env.example .env
composer install -q --no-ansi --no-interaction --no-scripts --no-progress --prefer-dist
chmod -R 777 storage bootstrap/cache
php artisan key:generate
php artisan config:clear

Enter fullscreen mode Exit fullscreen mode
# my-project/bin/ci-dusk

#!/usr/bin/env bash

php artisan dusk:chrome-driver `/opt/google/chrome/chrome --version | cut -d " " -f3 | cut -d "." -f1`
chmod -R 0755 vendor/laravel/dusk/bin/
php artisan serve  > /dev/null 2>&1 &
curl localhost:8000 &
./vendor/laravel/dusk/bin/chromedriver-linux > /dev/null 2>&1 &

Enter fullscreen mode Exit fullscreen mode

Simpy push your codes to github, and it should be good to go! Thank you for reading.

Honorable Mentions

  • Nasrul Hazim (Helping out with the workflow configurations)

Top comments (1)

Collapse
 
alphaolomi profile image
Alpha Olomi

Nice post, on a quick thought wouldn't it be better and abit faster if you used factories to make user data instead of seeding the data via an artisan call.