Cara Membatasi Jumlah Login Gagal di Laravel 8

wahyunanangwidodo

wahyunanangwidodo Senin, 16 Agustus 2021

Cara Membatasi Jumlah Login Gagal di Laravel 8

Biasanya ketika login pada suatu aplikasi dan gagal berulang kali, 3-5 kali misalnya, baik karena password atau email yang salah, akan ada jeda tunggu dengan batas waktu yang ditentukan untuk kemudian dapat mencoba kembali.

Metode tersebut atau yang biasa disebut penerapan Rate Limiting, dilakukan adalah untuk membatasi jumlah permintaan atau lalu lintas jaringan yang dilakukan berulang-ulang dalam jangka waktu tertentu.

Di laravel sendiri menyediakan fitur tersebut. Laravel menyediakan fitur yang dapat kita gunakan untuk membatasi jumlah permintaan ke route atau API pada aplikasi kita. Kita dapat menentukan berapa banyak atau kecepatan permintaan yang boleh dikirim dalam batas waktu tertentu.

Sebagai contoh dan cara penggunaannya, mari kita buat autentikasi login dengan menerapkan Rate Limiting.

Instalasi dan Database

Langkah pertama silahkan download laravel, buat database mysql dan mengaturnya pada file .env.

laravel new login
//.env
DB_DATABASE=login
DB_USERNAME=root
DB_PASSWORD=

Membuat User

Kita tambahkan user baru untuk digunakan saat login. Kita buat menggunakan seeding.

php artisan make:seeder UserSeeder

Buka UserSeeder.php, pada method run() buat seperti di bawah ini.

public function run()
{
    \DB::table('users')->insert([
        'name' => 'user',
        'email' => 'user@mail.com',
        'password' => bcrypt('12345678'),
        'created_at' => new \DateTime,
        'updated_at' => null,
    ]);
}

Lalu tambahkan class seeder pada DatabaseSeeder.php.

public function run()
{ 
    $this->call([ UserSeeder::class, ]);
}

Kemudian jalankan seeder sekaligus migrasi tabel.

php artisan migrate --seed

Postingan terkait seeding: Cara Seeding Data di Laravel 8

Membuat Halaman Login

Selanjutnya kita buat halaman login. Kita mulai dari membuat controller terlebih dahulu.

php artisan make:controller LoginController

Buka PostController.php, tambahkan metode create() di bawah ini.

<?php

namespace App\Http\Controllers; 
use Illuminate\Http\Request; 
 
class LoginController extends Controller
{
    public function create()
    {
        return view('login');
    }
}

Kemudian buat file baru dengan login.blade.php di direktori views dan tambahkan html di bawah ini.

 <!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Login</title>
    <style>
      body{background-color:#eee}.login-form{margin:0 auto;width:50%}
      .container{padding:2rem}.alert-css{margin-bottom:2rem}
      input{width:100%;margin-bottom:1rem;padding:.6rem}button{padding:.6rem}li{font-size:1.5rem}
    </style>
  </head>
  <body>
    <div class="container">
      <div class="login-form">
        @if ($errors->any())
        <div class="alert alert-css">
          <ul>
            @foreach ($errors->all() as $error)
            <li>{{ $error }}</li>
            @endforeach
          </ul>
        </div>
        @endif
        <form method="POST" action="{{ route('store')}}">
          @csrf
          <input type="text" name="email" placeholder="email">
          <input type="password" name="password" placeholder="password"> 
          <button type="submit">Submit</button>
        </form>
      </div>
    </div>
  </body>
</html> 
 

Setelah itu tambahkan route di bawah ini pada web.php.

use Illuminate\Http\Request;
use App\Http\Controllers\LoginController;

Route::get('/login', [LoginController::class, 'create'])->name('login');

Route::post('/store', [LoginController::class, 'store'])->name('store');

Route::middleware('auth')->get('/user', function (Request $request) {
    return $request->user();
})->name('user');

Jalankan php artisan serve, lalu buka http://localhost:8000/login untuk melihat hasilnya.

Autentikasi User Login

Kita lanjutkan ke pembuatan metode login dan penggunaan rate limiting.

Validasi Form Request

Sebelum mengerjakan metode login user, kita akan membuat validasi terlebih dahulu, dan kita gunakan 'form request' untuk validasi. Silahkan jalankan perintah di bawah ini.

php artisan make:request LoginRequest

Kemudian buka app\Http\LoginRequest.php, buat seperti di bawah ini.

<?php

namespace App\Http\Requests;

use Illuminate\Foundation\Http\FormRequest;
 
class LoginRequest extends FormRequest
{ 
    public function authorize()
    {
        return true;
    }
 
    public function rules()
    {
        return [
            'email' => 'required|string|email',
            'password' => 'required|string',
        ];
    }
}

Rate Limiting

Masih di LoginRequest.php, kita akan tambahkan metode penanganan login dan rate limiting.

Silahkan tambahkan metode authenticate() dan configureRateLimiting() beserta class yang dibutuhkan di bawah ini.

use Illuminate\Auth\Events\Lockout; 
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\RateLimiter; 
use Illuminate\Validation\ValidationException;

...

public function authenticate()
{
    $this->configureRateLimiting();

    $credentials = $this->only('email', 'password');

    if (! Auth::attempt($credentials)) { 

    RateLimiter::hit($this->input('email'), 60);
    
    throw ValidationException::withMessages(['error' => 'Email atau Password salah. Silahkan coba kembali!']);

    }  
} 

public function configureRateLimiting()
{
    $input = $this->input('email') ?: $this->ip();

    if (! RateLimiter::tooManyAttempts($input, 2)) {
        return;
    }  

    event(new Lockout($this));
    
    $seconds = RateLimiter::availableIn($input); 

    throw ValidationException::withMessages(['error' => 'Upaya masuk dibatasi. Coba kembali setelah ' . $seconds  . ' detik.']);
} 

Untuk mendefinisikan fungsi, kita gunakan class RateLimiter dengan method, parameter dan atau value. Pada metode configureRateLimiting() di atas, kita dapat menetapkan atau membatasi upaya login permenitnya dengan metode tooManyAttempts. Misalnya 2 kali, saat kita login dan gagal sebanyak 2 kali, user dengan email atau ip yang sama akan dikunci sementara dalam satu menit, atau dapat juga kita sesuaikan, dan akan menampilkan pesan error sepeti yang dibuat di atas.

Kemudian pada metode authenticate(), kita gunakan metode hit untuk proses waktu berjalan ketika terjadi kesalahan, dan 60 adalah lama waktu tunggu (60 detik). Waktu tunggu 60 detik ini akan mulai berjalan setelah terjadi kegagalan pertama, dan akan mengingat pengguna untuk kegagalan berikutnya. Jika pengguna gagal kembali di pencobaan berikutnya, waktu tunggu tidak mulai dari awal karena sudah terdaftar atau dalam antrian.

Setelah selesai di LoginRequest.php, kita menuju ke controller. Silahkan buka PostController.php, tambahkan metode store() dan panggil validasi form atau LoginRequest yang telah dibuat.

use App\Http\Requests\LoginRequest;

...

public function store(LoginRequest $request){

    $request->authenticate();

    $request->session()->regenerate(); 

    return redirect()->route('user'); 
}  

Sampai disini tinggal mencobanya. Jalankan php artisan serve, buka http://localhost:8000/login, kemudian login dengan email dan password yang telah dibuat.

  • email: user@mail.com
  • password: 12345678

Hasilnya seperti di bawah ini.

Cara Membatasi Jumlah Login Gagal di Laravel 8

Selesai

Itulah contoh dan cara penggunaan rate limiting pada autentikasi login di laravel. Silahkan dicoba dan dikembangkan.

Iklan Atas Artikel

Iklan Tengah Artikel 1

Iklan Tengah Artikel 2

Iklan Bawah Artikel

Berlangganan

Berlangganan untuk mendapat pemberitahuan artikel terbaru via email.