Kenapa Validation Error Tidak Muncul di Laravel Blade?

Kadang validasi Laravel sebenarnya sudah gagal, tetapi pesan error tidak tampil di Blade. Dari sisi user, hasilnya membingungkan: form seolah reload biasa, input lama hilang, atau tidak ada petunjuk field mana yang bermasalah.

Masalah ini biasanya bukan di validator Laravel, melainkan di cara form dan view menangani hasil validasi. Jadi fokus debugging-nya harus ke nama field, route middleware, session, dan cara Blade menampilkan $errors.

Kapan Masalah Ini Biasanya Muncul?

  • Form submit kembali ke halaman semula, tetapi tidak ada pesan apa pun
  • Input lama tidak muncul kembali setelah validasi gagal
  • Hanya sebagian field yang menampilkan error
  • Form Request dipakai, tetapi halaman terlihat "diam"
  • Request AJAX mengembalikan 422, tetapi UI tidak menampilkan pesan

Penyebab Paling Umum

1. Blade Tidak Menampilkan $errors

Laravel memang menyimpan error ke session, tetapi Blade tetap harus menampilkannya.

<input type="text" name="nama">

Tanpa blok @error('nama') atau daftar $errors->all(), user tidak akan melihat apa pun.

2. Nama Input Tidak Sama dengan Nama Rule

Kalau rule memakai title, tetapi input HTML bernama judul, error akan tersimpan untuk key title, bukan judul.

3. Route Tidak Lewat Middleware web

Untuk request web biasa, Laravel menyimpan error validasi dan old input lewat session. Kalau route tidak memakai stack web, mekanisme ini tidak tersedia.

4. authorize() di Form Request Mengembalikan false

Kalau method authorize() tidak diizinkan, request akan berhenti sebelum error validasi sampai ke Blade.

5. Request AJAX Belum Menangani Respons 422

Pada request JavaScript, Laravel biasanya mengembalikan JSON berisi error. Kalau frontend tidak membaca respons ini, user tetap tidak melihat apa-apa.

Langkah Diagnosis

  1. Pastikan validasi memang gagal dengan mencoba input kosong atau sengaja salah.
  2. Cek tab Network:
    • web form biasa biasanya redirect 302
    • AJAX biasanya mendapat 422 Unprocessable Entity
  3. Pastikan field di Blade dan aturan validasi memakai nama yang sama.
  4. Pastikan view menampilkan @error(...) atau $errors->all().
  5. Kalau memakai Form Request, cek method authorize().
Mulai dari Nama Field

Penyebab paling sering adalah mismatch sederhana: input bernama judul, tetapi error yang dicari di Blade adalah title.

Langkah Fix

1. Tampilkan Error Per Field

<input type="text" name="nama" value="{{ old('nama') }}">

@error('nama')
    <p style="color: red;">{{ $message }}</p>
@enderror

2. Tampilkan Ringkasan Semua Error

@if ($errors->any())
    <div>
        <ul>
            @foreach ($errors->all() as $error)
                <li>{{ $error }}</li>
            @endforeach
        </ul>
    </div>
@endif

3. Samakan Nama Input dan Rule

<?php

$request->validate([
    'judul' => 'required|min:3',
]);
<input type="text" name="judul" value="{{ old('judul') }}">

4. Pastikan Form Request Mengizinkan Request

<?php

public function authorize(): bool
{
    return true;
}

5. Tangani Error 422 di AJAX

const response = await fetch('/produk', {
  method: 'POST',
  headers: {
    'Content-Type': 'application/json',
    Accept: 'application/json',
    'X-CSRF-TOKEN': token,
  },
  body: JSON.stringify(payload),
});

if (response.status === 422) {
  const data = await response.json();
  console.log(data.errors);
}

Contoh Sebelum dan Sesudah

Sebelum

<input type="text" name="nama">

User tidak tahu kenapa form gagal karena error tidak pernah dirender.

Sesudah

<input type="text" name="nama" value="{{ old('nama') }}">

@error('nama')
    <small style="color: red;">{{ $message }}</small>
@enderror

Error Umum

Error Ada di Session, Tetapi Tidak Terlihat

Biasanya karena Blade tidak punya blok @error atau daftar $errors.

Input Lama Tidak Muncul

Periksa apakah field memakai value="{{ old('nama') }}" atau old() untuk textarea/select.

Form Request Dipakai, Tapi Langsung 403

Kemungkinan authorize() mengembalikan false, jadi masalahnya bukan di validasi.

Pencegahan

  1. Setiap field penting sebaiknya punya blok @error.
  2. Gunakan nama field yang konsisten dari HTML sampai validator.
  3. Untuk form besar, tampilkan juga ringkasan $errors->all().
  4. Pisahkan penanganan error untuk form biasa dan request AJAX.
  5. Jangan lupa old() agar pengalaman user tetap baik saat validasi gagal.

Bacaan Terkait

FAQ

Kenapa error validasi muncul di JSON, tetapi tidak di Blade?

Karena request kemungkinan dikirim sebagai AJAX atau frontend tidak merender pesan error yang dikembalikan Laravel.

Apakah wajib memakai @error di setiap field?

Tidak wajib, tetapi itu cara paling jelas agar user tahu field mana yang salah. Minimal sediakan satu ringkasan error global.

Kenapa validasi gagal, tetapi malah muncul error 419?

Itu masalah berbeda. Validasi belum sempat dijalankan karena request lebih dulu gagal di proteksi CSRF atau session.