laravel打印sql

快捷打印 Laravel 中的数据库查询(SQL)语句

 5天前 ⋅  375 ⋅  11 ⋅  11

闲话少叙,直接入题。首先,为什么要打印 Laravel 中 Query Builder 构建的 SQL 语句?

答案很简单,就是我要知道到底执行了什么 SQL 语句,这样我就能合适地写 Query Builder、在适合用『热加载』的场景不会误用『懒加载』。

热加载#

$user = User::where('name', 'Eric')->with('articles')->first();

上面就是热加载的例子――获取第一个名为『Eric』的用户信息同时,把他的文章也全都取到。

这样的使用场景下,Query Builder 只使用了类似下面的两条 SQL 语句。

  1. select * from users where name = 'Eric' limit 1;
  2. select * from articles where user_id in (22);

就是说当你用 $user->articles 遍历用户文章时,不会再请求数据库了。

懒加载#

懒加载和热加载是相对的。下面就是懒加载的例子。

$user = User::where('name', 'Eric')->first();

// 在 Blade 模版里遍历打印出用户文章
@\foreach($user->posts as $post)
    // ...
@endforeach

这种用法能达到效果,但是效率会变低――每次遍历、处理的一篇文章信息,都是向数据库执行一次 SQL 得到的。

如果用户有 N 篇文章,就要执行 N 次 SQL 查询,再加上之前请求用户信息的 1 次 SQL,这就是所谓的『N+1』问题。

明明能 2 次完成的事,就不要再花 N+1 次了。

打印 SQL#

像上面的状况,如果我们知道底层是怎样执行 SQL 语句的,也许就不会发生了。这就为我们找出了一个有必要打印 SQL 语句来看的理由。

既然文章题目是『快捷打印 SQL』,自然配置起来也很简单。配置到最后的结果的是:

当你的 APP_ENV 设置为 local、请求 URL 后面紧跟 ?sql-debug=1 时,就会打印出请求处理逻辑中涉及到的所有数据库查询语句。

配置#

AppServiceProvider 的 boot 方法内写入

use DB;
use Event;

if ( env('APP_ENV') === 'local' ) {
    DB::connection()->enableQueryLog();
    Event::listen('kernel.handled', function ( $request, $response ) {
        if ( $request->has('sql-debug') ) {
            $queries = DB::getQueryLog();
            if (!empty($queries)) {
                foreach ($queries as &$query) {
                    $query['full_query'] = vsprintf(str_replace('?', '%s', $query['query']), $query['bindings']);
                }
            }
            dd($queries);
        }
    });
}

注意:路由有两种形式——基于闭包(Closure)和基于控制器动作(Controller Action)的。上面的配置只对基于控制器动作的路由有效

转载于:https://my.oschina.net/u/2618337/blog/1236246

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值