首页 文章

Eloquent group在Laravel 5.3中使用有效的SQL查询生成“SQLSTATE [42000]”

提问于
浏览
6

我对Eloquent有一个奇怪的问题,我正在尝试执行以下操作:

$this->node = \DB::table('permission')
                ->select('permission.id',
                         'object.name as object_name',
                         'permission.created_at',
                         'object.id as object_id')
                ->join('object', 'object.id', '=', 'permission.object_id')
                ->join('action', 'action.id', '=', 'permission.action_id')
                ->where('permission.person_id', $this->person['id'])
                ->groupBy('permission.object_id')
                ->orderBy('permission.created_at', 'desc')
                ->paginate(5);

Laravel Framework 报告错误:

Connection.php第761行中的QueryException:SQLSTATE [42000]:语法错误或访问冲突:1055'permission.id'不在GROUP BY中(SQL:select permission.id,object.name as object_name,permission.created_at, object.id as object_id from object inner object object on object.id = permission.object_id inner join action on action.id = permission.action_id其中permission.person_id = 1 group by permission.object_id order by permission.created_at desc limit 5 offset 0 )

我在AppServiceProvider中添加了一个Eloquent调试函数 DB::listen

use Illuminate\Support\Facades\DB;
use Illuminate\Support\ServiceProvider;

class AppServiceProvider extends ServiceProvider
{
    /**
     * Bootstrap any application services.
     *
     * @return void
     */
    public function boot()
    {
        //
         DB::listen(function ($query) {

            echo "<pre>";
            print_r($query->sql);
            echo "</pre>";

            // $query->sql
            // $query->bindings
            // $query->time
        });
    }
    ...

它确实打印了这个SQL查询:

select  `permission`.`id`, 
        `object`.`name` as `object_name`, 
        `permission`.`created_at`, 
        `object`.`id` as `object_id` 
from `permission` 
inner join `object` on `object`.`id` = `permission`.`object_id` 
inner join `action` on `action`.`id` = `permission`.`action_id` 
where `permission`.`person_id` = 1 
group by `permission`.`object_id` 
order by `permission`.`created_at` desc 
limit 5 offset 0

哪个在MySQL中通过 PhpMyAdmin 有效,这里是查询的输出:
SQL Query Output
即便如此,我直接在 mysql 命令中测试它确实工作正常,看看mysql输出:

enter image description here

任何的想法?

谢谢

2 回答

  • 7

    laravel 5.3面临同样的问题他们正试图强制执行严格的查询写作 mysql-5.7

    但是要禁用此功能,只需转到 config/database.php 并更改 strict 标志

    'mysql' => [
                .
                .
                .
                'strict' => false,
                //'strict' => true,
                .
                .
            ],
    

    希望这也能解决你的问题 .

  • 8

    此查询针对sql标准,仅在某些sql模式设置下的mysql中有效 . 请参阅MySQL Handling of GROUP BY上的mysql文档:

    SQL92及更早版本不允许选择列表,HAVING条件或ORDER BY列表引用非聚合列的查询,这些列既不在GROUP BY子句中命名,也不在功能上依赖于(由GROUP BY列唯一确定) . 例如,此查询在标准SQL92中是非法的,因为选择列表中的非聚合名称列不出现在GROUP BY中:SELECT o.custid,c.name,MAX(o.payment)FROM orders AS o,customers AS c在哪里o.custid = c.custid GROUP BY o.custid;要使查询在SQL92中合法,必须从选择列表中省略name列,或在GROUP BY子句中命名 . SQL99及更高版本允许每个可选功能T301使用非聚合,如果它们在功能上依赖于GROUP BY列:如果name和custid之间存在这种关系,则查询是合法的 . 例如,这就是客户的主要关键 .

    您需要禁用only_full_group_by sql模式(它也是严格的sql模式的一部分),或者在选择列表中使用any_value()函数用于不在group by子句中的非聚合字段 .

    SELECT名称,ANY_VALUE(地址),MAX(年龄)FROM t GROUP BY名称;

相关问题