phpeloquentslimilluminate-containerphp-di

How to log every query from multiple connections in Eloquent (outside laravel)


I use multiple database connections in my app, one SQLServ, and another MySQL. I want to debug every query from both servers sequentially. therefore rather using Manager::getQueryLog() i need to use Event::listen. I use SlimFramework, with PHP-DI.

index.php

// Create container & database
$containerBuilder = new DI\ContainerBuilder(App\Lib\Container::class);
$containerBuilder->useAnnotations(false);
$containerBuilder->addDefinitions(__DIR__ . '/../config/settings.php');
$container = $containerBuilder->build();
$app = \DI\Bridge\Slim\Bridge::create($container);

// Register database
$capsule = new \Illuminate\Database\Capsule\Manager();
foreach ($container->get('database') as $con => $config) {
    $capsule->addConnection($config, $con);
}

$capsule->setEventDispatcher(new \Illuminate\Events\Dispatcher()); 
// Throw error A facade root has not been set. pretty sure it 
// was because i use it outside laravel

$capsule->setAsGlobal();
$capsule->bootEloquent();
$container->set('connection', $capsule);

// Listen
DB::listen(function($query) {
    Log::info(
       $query->sql,
       $query->bindings,
       $query->time
    );
});

App\Lib\Container::class

namespace App\Lib;

use DI\Container as DIContainer;

class Container extends DIContainer
{
    public function __get($key)
    {
        if ($this->has($key)) {
            return $this->get($key);
        }
    }
}

How to log every query from multiple connections, but in sequential order, something like the following.

select * from tableInMySQL limit 0,10;
select TOP 10 * from [tableInMSSQL];
update tableInMySQL set field='value';

EDIT

like I said earlier, I use SlimFramework, with PHP-DI.
So, I'm not use LARAVEL as a whole. (not using service provider)

the DB::listen throw error, $capsule->getConnection('con_name')->getEventDispatcher() return null


Solution

  • To log queries of multiple db connections in sequential order, we'll need to enableQueryLog first, have separate Logger configured.

    $capsule->setAsGlobal();
    $capsule->bootEloquent();
    $container->set('connection', $capsule);
    
    $capsule->connection('<MySqlConnectionName>')->enableQueryLog();
    $capsule->connection('<SqlServerConnectionName>')->enableQueryLog();
    //$capsule->connection('<MongoConnectionName>')->enableQueryLog(); 
    
    // Listen
    \Illuminate\Database\Capsule\Manager::listen(function($query) {
        if($query->connectionName == 'mysql') {
            $mysqlLogger->debug('mysql', [
                'query' => $query->sql,
                'bindings' => $query->bindings
            ]);
        } elseif($query->connectionName == 'sqlserver') {
            $sqlServerLogger->debug('mongodb', [
                'query' => $query->sql,
                'bindings' => $query->bindings
            ]);
        } /*elseif($query->connectionName == 'mongodb') {
            $mongoDbLogger->debug('mongodb', [
                'query' => $query->sql,
                'bindings' => $query->bindings
            ]);
        }*/
    });