【问题标题】:Route model binding with multiple wildcards具有多个通配符的路由模型绑定
【发布时间】:2021-08-13 04:55:00
【问题描述】:

如何明确表示路由模型绑定以仅获取相关类别?我的 web.php 文件如下:

Route::get('/catalog/{category}', [CategoryController::class, 'index'])->name('category.index');
Route::get('/catalog/{category}/{subcategory}', [SubcategoryController::class, 'index'])->name('subcategory.index');
Route::get('/catalog/{category}/{subcategory}/{subsubcategory}', [SubsubcategoryController::class, 'index'])->name('subsubcategory.index');

子子类别控制器:

public function index(Category $category, Subcategory $subcategory, Subsubcategory $subsubcategory)
{
    $subsubcategory->load('product')->loadCount('product');
    $products = Product::where('subsubcategory_id', $subsubcategory->id)->orderByRaw('product_order = 0, product_order')->get();
 return view('subsubcategory.index', compact('subsubcategory', 'products'));
}

和有问题的模型:

public function subcategory()
{
    return $this->belongsTo(Subcategory::class);
}

public function category()
{
    return $this->belongsTo(Category::class);
}

public function getRouteKeyName()
{
    return 'slug';
}

它部分工作正常。它加载了所有的蛞蝓,但问题是,假设我有三星子类别,它的父类别如下:

目录/手机/android/三星

每当我将 url 从 catalog/mobile-phones/android/samsung 修改为 catalog/mobile-phones/ios/samsung 时,它都可以工作,实际上它不应该.如何处理第二种情况?

PS:如果我打开子类别并更改类别 slug,它也适用。但是,很明显,如果上层类别不存在,它会抛出 404。

【问题讨论】:

  • 尝试颠倒列出的路线,改为此顺序 ``` Route::get('/catalog/{category}/{subcategory}/{subsubcategory}', [SubsubcategoryController::class, 'index'])->name('subsubcategory.index'); Route::get('/catalog/{category}/{subcategory}', [SubcategoryController::class, 'index'])->name('subcategory.index'); Route::get('/catalog/{category}', [CategoryController::class, 'index'])->name('category.index'); ```
  • 感谢您的回复,但功能还是一样

标签: laravel routes route-model-binding


【解决方案1】:

您可能想稍微探索一下有关显式路由模型绑定和自定义解析逻辑的文档以获得一些想法。
https://laravel.com/docs/8.x/routing#customizing-the-resolution-logic

以下内容未经测试,我正在对您的表结构进行一些猜测,但我认为这应该为您提供如何更改路由模型绑定以满足您的需求的基本概念。相同的概念也可以应用于{subcategory} 绑定,但少了一次关系检查。

App/Providers/RouteServiceProvider.php

public function boot()
{
    // ...default code...

    // add custom resolution for binding 'subsubcategory'
    Route::bind('subsubcategory', function($slug, $route) {

        // check to see if category exists
        if ($category = Category::where('slug',$route->parameter('category'))->first()) {

            // check to see if subcategory exists under category
            if ($subcategory = $category->subcategories()->where('slug',$route->parameter('subcategory'))->first()) {

                // check to see if subsubcategory exists under subcategory
                if ($subsubcategory = $subcategory->subsubcategories()->where('slug',$slug)->first()) {

                    // success, proper relationship exists
                    return $subsubcategory;
                }
            }
        }

        // fail (404) if we get here
        throw new ModelNotFoundException();
    });
}

但是,我会注意到,这会产生许多单独的数据库调用。如果考虑优化,可能有更有效的方法可以通过其他方法实现相同的目标。

【讨论】:

    猜你喜欢
    • 2015-07-02
    • 2021-01-05
    • 1970-01-01
    • 1970-01-01
    • 2018-01-08
    • 2017-01-10
    • 1970-01-01
    • 1970-01-01
    • 2023-03-11
    相关资源
    最近更新 更多