Berikut adalah tutorial lengkap untuk Email Verification dan Custom Password Reset di Laravel. Namun sebelum ke tutorlal ini, ada baiknya mengikuti tutorial sebelumnya
Persiapan Awal
- Laravel versi terbaru (Laravel 10) harus sudah diinstal.
- Database sudah dikonfigurasi di .env dan tabel sudah dimigrasi.
- Laravel Breeze untuk scaffolding autentikasi juga disarankan. Jika belum, jalankan:
composer require laravel/breeze --dev
php artisan breeze:install
php artisan migrate
Langkah 1: Mengaktifkan Verifikasi Email
1.1 Mengaktifkan Middleware Verifikasi Email
Untuk data user, kita akan pakai data sebelumnya pada tutorial Membuat Multi-Authentication System di Laravel Login Admin dan User. Silahkan mengikuti tutorial sebelumnya untuk detailnya
Tambahkan middleware verified pada route yang ingin dilindungi. Buka routes/web.php:
use Illuminate\Support\Facades\Route;
Route::middleware(['auth', 'verified','role:user'])->group(function () {
Route::get('/user/dashboard', function () {
return view('user.dashboard');
})->name('user.dashboard');
});
Hal ini akan melakukan verifikasi setiap melakukan login yang dikirim ke email.
1.2 Mengaktifkan Fitur Verifikasi di Model User
Di file app/Models/User.php, implementasikan MustVerifyEmail:
use Illuminate\Contracts\Auth\MustVerifyEmail;
class User extends Authenticatable implements MustVerifyEmail
{
// Konfigurasi verifikasi email siap digunakan
}
1.3 Menyesuaikan View Verifikasi Email
Jika ingin mengubah tampilan, buat resources/views/auth/verify-email.blade.php:
@extends('layouts.app')
@section('content')
<div>
<h1>Email Verification</h1>
<p>Check your email to verify your account.</p>
@if (session('status') == 'verification-link-sent')
<p>A new verification link has been sent to your email address.</p>
@endif
<form method="POST" action="{{ route('verification.send') }}">
@csrf
<button type="submit">Resend Verification Email</button>
</form>
</div>
@endsection
1.4 Pengujian Verifikasi Email
Setelah pendaftaran, pengguna akan diminta verifikasi email dan diarahkan ke halaman tersebut. Verifikasi akun dengan mengklik link pada email.
Kita akan menggunakan https://mailtrap.io untuk konfigurasi SMTP mailer nya. jika belum registrasi, silahkan registrasi dan login ke akun mailtrap. Setelah login, buka menu INBOXES lalu ada SMTP untuk kita lakukan testing seperti berikut:
Setelah dapat, edit file .env di laravel menjadi sebagai berikut:
MAIL_MAILER=smtp
MAIL_HOST=sandbox.smtp.mailtrap.io
MAIL_PORT=2525
MAIL_USERNAME=304a002842dcf4
MAIL_PASSWORD=********6a30
Sesuaikan config SMTP dengan config SMTP di mailtrap anda. Setelah itu kita akan testing login menggunakan URL berikut:
http://localhost:8000/login
Setelah itu akan muncul verifikasi sebagai sebagai berikut:
Cek di inbox mailtrap, dan akan menghasilkan seperti berikut:
Langkah 2: Mengatur Custom Password Reset
2.1 Membuat Notifikasi Reset Password
Buka file app/Notifications/ResetPasswordNotification.php atau jika belum ada, bisa dibuat dengan:
php artisan make:notification ResetPasswordNotification
Edit ResetPasswordNotification.php untuk menyesuaikan isi email:
namespace App\Notifications;
use Illuminate\Notifications\Notification;
use Illuminate\Notifications\Messages\MailMessage;
class ResetPasswordNotification extends Notification
{
public $token;
public function __construct($token)
{
$this->token = $token;
}
public function via(object $notifiable): array
{
return ['mail'];
}
public function toMail($notifiable)
{
return (new MailMessage)
->subject('Reset Your Password')
->line('You are receiving this email because we received a password reset request for your account.')
->action('Reset Password', url(route('password.reset', $this->token, false)))
->line('If you did not request a password reset, no further action is required.');
}
}
2.2 Update Model User untuk menggunakan Notifikasi
Di app/Models/User.php, tambahkan method sendPasswordResetNotification:
use App\Notifications\ResetPasswordNotification;
public function sendPasswordResetNotification($token)
{
$this->notify(new ResetPasswordNotification($token));
}
2.3 Membuat Route dan View untuk Password Reset
Tambahkan route untuk mengelola password reset di routes/web.php:
use Illuminate\Support\Facades\Password;
use Illuminate\Http\Request;
Route::get('/forgot-password', function () {
return view('auth.forgot-password');
})->middleware('guest')->name('password.request');
Route::post('/forgot-password', function (Request $request) {
$request->validate(['email' => 'required|email']);
$status = Password::sendResetLink(
$request->only('email')
);
return $status === Password::RESET_LINK_SENT
? back()->with(['status' => __($status)])
: back()->withErrors(['email' => __($status)]);
})->middleware('guest')->name('password.email');
Route::get('/reset-password/{token}', function ($token) {
return view('auth.reset-password', ['token' => $token]);
})->middleware('guest')->name('password.reset');
Route::post('/reset-password', function (Request $request) {
$request->validate([
'token' => 'required',
'email' => 'required|email',
'password' => 'required|min:8|confirmed',
]);
$status = Password::reset(
$request->only('email', 'password', 'password_confirmation', 'token'),
function ($user, $password) {
$user->forceFill([
'password' => bcrypt($password)
])->save();
}
);
return $status === Password::PASSWORD_RESET
? redirect()->route('login')->with('status', __($status))
: back()->withErrors(['email' => [__($status)]]);
})->middleware('guest')->name('password.update');
2.4 Membuat View untuk Password Reset
Forgot Password View (resources/views/auth/forgot-password.blade.php)
@extends('layout')
@section('content')
<h1>Forgot Password</h1>
<form action="{{ route('password.email') }}" method="POST">
@csrf
<div class="mb-3">
<label for="email" class="form-label">Email:</label>
<input type="email" class="form-control" id="email" name="email" required>
<div id="emailHelp" class="form-text">We'll never share your email with anyone else.</div>
<button type="submit" class="btn btn-primary mt-50">Send Password Reset Link</button>
</div>
</form>
@endsection
Reset Password View (resources/views/auth/reset-password.blade.php)
@extends('layout')
@section('content')
<h1>Reset Password</h1>
<form action="{{ route('password.update') }}" method="POST">
@csrf
<div class="mb-3">
<input type="hidden" name="token" value="{{ $request->route('token') }}">
<label for="email">Email:</label>
<input type="email" id="email" class="form-control" name="email" required>
</div>
<div class="mb-3">
<label for="password">New Password:</label>
<input type="password" id="password" class="form-control" name="password" required>
</div>
<div class="mb-3">
<label for="password_confirmation">Confirm Password:</label>
<input type="password" id="password_confirmation" class="form-control" name="password_confirmation" required>
</div>
<button type="submit" class="btn btn-primary">Reset Password</button>
</form>
@endsection
Silahkan testing dengan akses URL login kemudian klik Forgot your password? hasilnya seperti berikut:
Jika berhasil, maka akan tampil seperti berikut di inboxes mailtrap:
Setelah klik Reset Password, akan diarahkan ke halaman change password berikut: