Skip to content

Instantly share code, notes, and snippets.

@kynetiv
Last active February 28, 2019 00:54
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save kynetiv/b16de900a5d1d624b6283bf0d95b169a to your computer and use it in GitHub Desktop.
Save kynetiv/b16de900a5d1d624b6283bf0d95b169a to your computer and use it in GitHub Desktop.
Laravel Multi-tenant event listener for Hyn\Tenancy\Events\Database\Creating event. Workaround for RDS and MySQL 5.6 (related: https://github.com/hyn/multi-tenant/issues/660)
<?php
namespace App\Listeners;
use Hyn\Tenancy\Database\Connection;
use Hyn\Tenancy\Events;
use Hyn\Tenancy\Events\Database\Creating;
use Hyn\Tenancy\Traits\DispatchesEvents;
use Illuminate\Queue\InteractsWithQueue;
use Illuminate\Contracts\Queue\ShouldQueue;
use Illuminate\Database\Connection as IlluminateConnection;
use Illuminate\Contracts\Events\Dispatcher;
class TenantDatabaseCreating
{
use DispatchesEvents;
protected $connection;
public function __construct(Connection $connection)
{
$this->connection = $connection;
}
/**
* Handle the event.
*
* @param Creating $event
* @return void
*/
public function onDatabaseCreating(Creating $event)
{
/* NOTE: We need to override the tenancy database user and database creation for our current MySQL 5.6 as well as an issue with RDS (see https://github.com/hyn/multi-tenant/issues/660) */
/* For v5.3.1 of the hyn/multi-tenant package, we don't have the solution for issue #660 merged in yet so we'll temporarily fix it here and make it work for MySQL 5.6 */
/* Basically we hijack the creation before the package would do so, and then we'll set the flag so the package doesn't try to create the user and the database after us*/
$create = function ($connection) use ($event) {
return $connection->statement("CREATE DATABASE IF NOT EXISTS `{$event->config['database']}`
DEFAULT CHARACTER SET {$event->config['charset']}
DEFAULT COLLATE {$event->config['collation']}");
};
$user = function ($connection) use ($event) {
return $connection->statement("GRANT ALL ON `{$event->config['database']}`.* TO `{$event->config['username']}`@'{$event->config['host']}' IDENTIFIED BY '{$event->config['password']}'");
};
$this->connection->system($event->website)->transaction(function (IlluminateConnection $connection) use ($user, $create) {
return $create($connection) && $user($connection);
});
// Necessary to set the create db config to `false` here so multi-tenant doesn't try to.
// May need to turn it back on in an Hyn\Tenancy\Events\Database\Created event listener.
config(['tenancy.db.auto-create-tenant-database' => false]);
}
/**
* Register the listeners for the subscriber.
*
*/
public function subscribe(Dispatcher $events)
{
$events->listen(
'Hyn\Tenancy\Events\Database\Creating',
'App\Listeners\TenantDatabaseCreating@onDatabaseCreating'
);
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment