Laravel 查询构建器与 Raw
Laravel query builder vs Raw
我是 laravel 的新手,到目前为止我非常喜欢 eloquent 和查询生成器,但是一旦查询变得更加复杂,我的头就开始疼了...我刚刚完成一段时间后有 2 个工作示例,也许你们可以帮助我优化它。我将首先给出示例,然后是(缺点)优点
所以首先 DB::select...老实说,我认为它比第二个示例更具可读性..或者我只是在构建器上做错了 xD。
$shared_slugs = Magic::in_query($this->shared_slugs);
$items = DB::select("
SELECT * FROM f_admin_items
WHERE
active = 1
AND (
slug IN $shared_slugs
OR
:treshhold <= :urank AND id IN (SELECT admin_item_id FROM f_user_access WHERE user_id = :uid)
OR
:treshhold > :urank AND `rank` >= :urank
)
ORDER BY `order` ASC
", [
'treshhold' => $this->threshold_rank,
'urank' => $user_rank,
'uid' => $user_id
]);
命名参数绑定总体上非常有效。基本上,菜单项必须始终处于活动状态,加上 (1 OR 2 OR 3 )。例如仪表板被接受为共享 slug.. 否则会有一些排名检查。
现在我一直在努力使用 eloquent en query builder =/ 我认为没有必要建立关系,因为我只将它用于菜单和中间件。在这种情况下,仅包含 admin_item_id 和 user_id 的 f_user_access table 并没有真正起到枢轴的作用,也没有在其他任何地方使用。
$items =
$this->where( 'active', 1 )
->where( function ($query) {
$query->whereIn( 'slug', $this->shared_slugs )
->orWhere(function ($query) {
$query->whereRaw( $this->threshold_rank.' <= '.$this->user_rank )
->whereIn('id', function ($query) {
$query->select('admin_item_id')->from('f_user_access')->where('user_id', $this->user_id)->get();
});
})
->orWhere(function ($query) {
$query->whereRaw( $this->threshold_rank.' > '.$this->user_rank )
->where( 'rank', '>=', $this->user_rank );
});
})->orderBy( 'order', 'ASC' )->get();
我喜欢第二个的原因是我可以将 $shared_slugs 作为数组传递,而不必先将其转换为字符串。但除此之外,我真的很讨厌这个的外观,where(function($query){}) 等等......除此之外,传递给这个函数的 $ids 在 where.functions 中不可访问,所以我必须先在 class 中定义它们。
我喜欢的第一个是因为它的命名绑定,而且读起来还不错:S,而且变量是可访问的。不利的是,我必须调用这个函数来将共享的 slugs 转换成一个大批。
不使用 eloquent 和 querybuilder 真的有那么糟糕吗?至少在某些情况下......你们会怎么做才能使第二个例子更好? =/
更新::
由于答案和反馈,我放弃了原始 sql。当前函数中有 5 个范围,并且为 user_access.
制作了一个(小)模型
$items =
$this->active() //Only active items AND... 1, 2 or 3
->where( function ($query) {
$query->shared_slug() // 1
->orWhere(function ($query) { // OR 2
$query->access_required()
->whereIn('id', UserAccess::get_access( $this->user_id ) );
})
->orWhere(function ($query) { // OR 3
$query->no_access_required()
->whereRaw( 'rank >= '.$this->user_rank );
});
})->ASC()->get();
使用查询生成器的主要好处是它使您脱离了所选存储所使用的语言,即 MySQL、Oracle、SQLite 等。如果您曾经切换数据库类型,您可能会遇到大量重构原始 SQL。相信我,当您开始一个项目并了解情况时,情况并不好。
然而,总有一些注意事项,这正是 Eloquent 也能够使用原始语句的原因。
我是 laravel 的新手,到目前为止我非常喜欢 eloquent 和查询生成器,但是一旦查询变得更加复杂,我的头就开始疼了...我刚刚完成一段时间后有 2 个工作示例,也许你们可以帮助我优化它。我将首先给出示例,然后是(缺点)优点
所以首先 DB::select...老实说,我认为它比第二个示例更具可读性..或者我只是在构建器上做错了 xD。
$shared_slugs = Magic::in_query($this->shared_slugs);
$items = DB::select("
SELECT * FROM f_admin_items
WHERE
active = 1
AND (
slug IN $shared_slugs
OR
:treshhold <= :urank AND id IN (SELECT admin_item_id FROM f_user_access WHERE user_id = :uid)
OR
:treshhold > :urank AND `rank` >= :urank
)
ORDER BY `order` ASC
", [
'treshhold' => $this->threshold_rank,
'urank' => $user_rank,
'uid' => $user_id
]);
命名参数绑定总体上非常有效。基本上,菜单项必须始终处于活动状态,加上 (1 OR 2 OR 3 )。例如仪表板被接受为共享 slug.. 否则会有一些排名检查。
现在我一直在努力使用 eloquent en query builder =/ 我认为没有必要建立关系,因为我只将它用于菜单和中间件。在这种情况下,仅包含 admin_item_id 和 user_id 的 f_user_access table 并没有真正起到枢轴的作用,也没有在其他任何地方使用。
$items =
$this->where( 'active', 1 )
->where( function ($query) {
$query->whereIn( 'slug', $this->shared_slugs )
->orWhere(function ($query) {
$query->whereRaw( $this->threshold_rank.' <= '.$this->user_rank )
->whereIn('id', function ($query) {
$query->select('admin_item_id')->from('f_user_access')->where('user_id', $this->user_id)->get();
});
})
->orWhere(function ($query) {
$query->whereRaw( $this->threshold_rank.' > '.$this->user_rank )
->where( 'rank', '>=', $this->user_rank );
});
})->orderBy( 'order', 'ASC' )->get();
我喜欢第二个的原因是我可以将 $shared_slugs 作为数组传递,而不必先将其转换为字符串。但除此之外,我真的很讨厌这个的外观,where(function($query){}) 等等......除此之外,传递给这个函数的 $ids 在 where.functions 中不可访问,所以我必须先在 class 中定义它们。
我喜欢的第一个是因为它的命名绑定,而且读起来还不错:S,而且变量是可访问的。不利的是,我必须调用这个函数来将共享的 slugs 转换成一个大批。
不使用 eloquent 和 querybuilder 真的有那么糟糕吗?至少在某些情况下......你们会怎么做才能使第二个例子更好? =/
更新::
由于答案和反馈,我放弃了原始 sql。当前函数中有 5 个范围,并且为 user_access.
制作了一个(小)模型 $items =
$this->active() //Only active items AND... 1, 2 or 3
->where( function ($query) {
$query->shared_slug() // 1
->orWhere(function ($query) { // OR 2
$query->access_required()
->whereIn('id', UserAccess::get_access( $this->user_id ) );
})
->orWhere(function ($query) { // OR 3
$query->no_access_required()
->whereRaw( 'rank >= '.$this->user_rank );
});
})->ASC()->get();
使用查询生成器的主要好处是它使您脱离了所选存储所使用的语言,即 MySQL、Oracle、SQLite 等。如果您曾经切换数据库类型,您可能会遇到大量重构原始 SQL。相信我,当您开始一个项目并了解情况时,情况并不好。
然而,总有一些注意事项,这正是 Eloquent 也能够使用原始语句的原因。