Generate The Raw MySQL Query From Laravel Query Builder

后端 未结 14 1172
醉话见心
醉话见心 2021-02-02 12:04

How can i get mysql query of a laravel query

Convert:

App\\User::where(\'balance\',\'>\',0)->where(...)-         


        
相关标签:
14条回答
  • 2021-02-02 12:42

    In Laravel 5.4 (I didn't check this in other versions), add this function into the "App"=>"Providers"=>"AppServiceProvider.php" .

    public function boot()
    {
    
        if (App::isLocal()) {
    
            DB::listen(
                function ($sql) {
                    // $sql is an object with the properties:
                    //  sql: The query
                    //  bindings: the sql query variables
                    //  time: The execution time for the query
                    //  connectionName: The name of the connection
    
                    // To save the executed queries to file:
                    // Process the sql and the bindings:
                    foreach ($sql->bindings as $i => $binding) {
                        if ($binding instanceof \DateTime) {
                            $sql->bindings[$i] = $binding->format('\'Y-m-d H:i:s\'');
                        } else {
                            if (is_string($binding)) {
                                $sql->bindings[$i] = "'$binding'";
                            }
                        }
                    }
    
                    // Insert bindings into query
                    $query = str_replace(array('%', '?'), array('%%', '%s'), $sql->sql);
    
                    $query = vsprintf($query, $sql->bindings);
    
                    // Save the query to file
                    /*$logFile = fopen(
                        storage_path('logs' . DIRECTORY_SEPARATOR . date('Y-m-d') . '_query.log'),
                        'a+'
                    );*/
                    Log::notice("[USER] $query");
                }
            );
        }
    }
    

    After that install, https://github.com/ARCANEDEV/LogViewer and then you can see every executed SQL queries without editing the code.

    0 讨论(0)
  • 2021-02-02 12:43

    Here is a helper function who tells you the last SQL executed.

    use DB;
    public static function getLastSQL()
    {
        $queries = DB::getQueryLog();
        $last_query = end($queries);
              // last_query is the SQL with with data binding like 
              //   { 
              //       select ? from sometable where field = ? and field2 = ? ;
              //       param1,
              //       param2,
              //       param3,
              //   }
              //   which is hard to read.
        $last_query = bindDataToQuery($last_query);     
              // here, last_query is the last SQL you have executed as normal SQL
              //     select param1 from sometable where field=param2 and field2 = param3;
        return $last_query
    }
    

    Here is the bindDataToQuery function, who fill the '?' blanks with real params.

    protected static function bindDataToQuery($queryItem){
        $query = $queryItem['query'];
        $bindings = $queryItem['bindings'];
        $arr = explode('?',$query);
        $res = '';
        foreach($arr as $idx => $ele){
            if($idx < count($arr) - 1){
                $res = $res.$ele."'".$bindings[$idx]."'";
            }
        }
        $res = $res.$arr[count($arr) -1];
        return $res;
    }
    
    0 讨论(0)
  • 2021-02-02 12:43

    To print the raw sql query, try:

    DB::enableQueryLog();
    // Your query here
    $queries = DB::getQueryLog();
    print_r($queries);
    

    Reference

    0 讨论(0)
  • 2021-02-02 12:48

    use toSql() method of laravel to get the query to be executed like

    App\User::where('balance','>',0)->where(...)->toSql();
    

    But Laravel will not show you parameters in your query, because they are bound after preparation of the query. To get the bind parameters, use this

    $query=App\User::where('balance','>',0)->where(...);
    print_r($query->getBindings() );
    

    enable the query log as DB::enableQueryLog() and then output to the screen the last queries ran you can use this,

    dd(DB::getQueryLog());
    
    0 讨论(0)
  • 2021-02-02 12:48

    It is so strange that the laravel haven't support any way to get the raw sql easily, it is now version 6 after all...

    Here's a workaround I used by myself to quickly get the raw sql with parameters without installing any extension...

    Just deliberately make your original sql WRONG

    Like change

    DB::table('user')
    

    to

    DB::table('user1')
    

    where the table "user1" does not exist at all!

    Then run it again.

    Sure there will be an exception reported by laravel.

    SQLSTATE[42S02]: Base table or view not found: 1146 Table 'user1' doesn't exist (SQL: ...)
    

    And now you can see the raw sql with parameters is right after the string "(SQL:"

    Change back from the wrong table name to the right one and there you go!

    0 讨论(0)
  • 2021-02-02 12:48

    Instead of interfering with the application with print statements or "dds", I do the following when I want to see the generated SQL:

    DB::listen(function ($query) { 
        Log::info($query->sql, $query->bindings);
    });
    
    // (DB and Log are the facades in Illuminate\Support\Facades namespace)
    

    This will output the sql to the Laravel log (located at storage/logs/laravel.log). A useful command for following writes to this file is

    tail -n0 -f storage/logs/laravel.log
    
    0 讨论(0)
提交回复
热议问题