Eloquent多URL参数过滤查询构建问题
Eloquent多URL参数过滤查询构建问题
嘿,我刚接触Eloquent Query Builder,现在遇到个查询构建的问题想求助:
我的需求是:写一个查询语句,根据四个选择器的参数来筛选出匹配的食谱,这四个选择器分别是:
- 菜品分类
- 菜品子分类
- 菜系
- 菜单
有个很重要的细节要说明:这些选择器有依赖关系,不能在没选择菜品分类的情况下直接选择菜品子分类。
针对这个需求,我来给你一步步拆解实现思路哈:
首先,我们可以通过链式动态条件判断来拼接查询,既能灵活处理不同的参数组合,还能严格遵守子分类依赖分类的规则。
基础实现方案
- 先初始化查询实例,假设你的食谱模型是
Recipe - 逐个检查URL传过来的参数,只有参数存在且有效时,才添加对应的过滤条件
- 处理子分类时,先判断分类参数是否存在,避免出现无分类选子分类的违规情况
具体代码可以这么写:
// 从请求里获取参数,这里用Laravel的Request类来取 $category = request()->input('dish_category'); $subcategory = request()->input('dish_subcategory'); $cuisine = request()->input('cuisine'); $menu = request()->input('menu'); // 初始化查询实例 $query = \App\Models\Recipe::query(); // 先处理菜品分类过滤 if (!empty($category)) { $query->where('dish_category_id', $category); // 只有分类存在时,才处理子分类的过滤 if (!empty($subcategory)) { $query->where('dish_subcategory_id', $subcategory); } } // 处理菜系过滤 if (!empty($cuisine)) { $query->where('cuisine_id', $cuisine); } // 处理菜单过滤 if (!empty($menu)) { $query->where('menu_id', $menu); } // 执行查询拿到结果 $recipes = $query->get();
更简洁的优化写法
Laravel的查询构建器有个when()语法糖,专门用来简化条件查询,用它的话代码会更清爽,而且逻辑更直观:
$recipes = \App\Models\Recipe::when(request('dish_category'), function ($query, $category) { // 分类存在时,先加分类过滤,再嵌套判断子分类 $query->where('dish_category_id', $category) ->when(request('dish_subcategory'), function ($query, $subcategory) { $query->where('dish_subcategory_id', $subcategory); }); })->when(request('cuisine'), function ($query, $cuisine) { $query->where('cuisine_id', $cuisine); })->when(request('menu'), function ($query, $menu) { $query->where('menu_id', $menu); })->get();
when()方法会自动判断参数是否有效(非空、非false),只有满足条件时才执行闭包里的查询逻辑,完全不用自己写一堆if判断,非常符合Laravel的优雅风格~
额外小提醒
- 可以在
Recipe模型里给这些关联字段定义belongsTo关联,比如public function category() { return $this->belongsTo(DishCategory::class); },后续要连表查询或者预加载关联数据会更方便 - 建议给请求参数加一层验证,比如在请求类里验证
dish_category是否是数据库中存在的分类ID,避免无效参数导致的错误查询
备注:内容来源于stack exchange,提问作者dmytroshved
相关产品推荐
相关产品推荐

