Laravel 8路由模型绑定触发404错误,求排查方案
Laravel 8路由模型绑定404错误排查
问题描述
在Laravel 8中使用路由模型绑定时触发404错误,自查路由和控制器未定位到问题,以下是相关代码及排查方案:
相关代码
视图代码(index页面)
<h1 class="heading"> product <span>categories</span> </h1> <div class="box-container"> @foreach($kategori as $k) <div class="box"> <img src="image/cat-1.png" alt=""> <h3>{{$k->nama_kategori}}</h3> <p>{{$k->deskripsi_kategori}}</p> <a href="/{{$k->slug_kategori}}" class="btn">Lihat</a> </div> @endforeach </div>
路由代码
<?php use App\Http\Controllers\HomepageController; use Illuminate\Support\Facades\Route; Route::get('/', [HomepageController::class, 'index']); Route::get('/{buku:slug}', [HomepageController::class, 'show']); Route::get('/{kategori:slug_kategori}', [HomepageController::class, 'lihat']);
控制器代码
<?php namespace App\Http\Controllers; use Illuminate\Http\Request; use App\Models\Buku; use App\Models\Kategori; class HomepageController extends Controller { public function index() { return view('homepage/index',[ "title" => "Homepage", "books" => Buku::all(), "kategori" => Kategori::all(), ]); } public function show(Buku $buku) { return view('homepage/lihat', [ 'title' => 'Detail Buku', 'book' => $buku ]); } public function lihat(Kategori $kategori) { return view('homepage/kategori', [ 'title' => $kategori->nama, 'kategoris' => $kategori, ]); } }
Kategori迁移文件
<?php use Illuminate\Database\Migrations\Migration; use Illuminate\Database\Schema\Blueprint; use Illuminate\Support\Facades\Schema; return new class extends Migration { public function up() { Schema::create('kategoris', function (Blueprint $table) { $table->id(); $table->string('kode_kategori')->unique(); $table->string('nama_kategori')->unique(); $table->string('slug_kategori'); $table->text('deskripsi_kategori'); $table->timestamps(); }); } public function down() { Schema::dropIfExists('kategoris'); } };
排查方案
1. 路由顺序冲突(核心问题)
当前路由中,/{buku:slug} 定义在 /{kategori:slug_kategori} 之前,所有根路径下的slug请求会优先匹配书籍路由。当请求的slug不存在于Buku模型时,Laravel直接返回404,不会进入分类路由的匹配流程。
解决方法:
- 推荐给路由添加前缀,彻底避免冲突:
同时更新视图中的分类链接:Route::get('/', [HomepageController::class, 'index']); Route::get('/buku/{buku:slug}', [HomepageController::class, 'show']); Route::get('/kategori/{kategori:slug_kategori}', [HomepageController::class, 'lihat']);<a href="/kategori/{{$k->slug_kategori}}" class="btn">Lihat</a> - 若坚持使用根路径,需确保分类与书籍的slug完全不重复,并将分类路由调整到书籍路由之前:
此方式存在后续slug重复导致错误的风险,不推荐。Route::get('/', [HomepageController::class, 'index']); Route::get('/{kategori:slug_kategori}', [HomepageController::class, 'lihat']); Route::get('/{buku:slug}', [HomepageController::class, 'show']);
2. 控制器字段错误
lihat方法中使用了$kategori->nama,但迁移文件中对应的字段是nama_kategori,会导致视图渲染错误,需修正:
public function lihat(Kategori $kategori) { return view('homepage/kategori', [ 'title' => $kategori->nama_kategori, 'kategoris' => $kategori, ]); }
3. 数据验证
确认数据库中kategoris表的slug_kategori字段存在对应的值,可通过以下代码验证:
// 在控制器或路由中临时添加 dd(Kategori::where('slug_kategori', '你的测试slug')->first());
若返回null,说明数据库中无对应记录,需检查数据填充逻辑。
内容的提问来源于stack exchange,提问作者Dodek Mardana
相关产品推荐
相关产品推荐

