From 7d98ebb5d177a1ac30ec0a7d248c4cd254abce4a Mon Sep 17 00:00:00 2001 From: Victor R <39545521+viicslen@users.noreply.github.com> Date: Wed, 1 Jun 2022 10:12:59 -0400 Subject: [PATCH] [4.x] Add tenant schema dump command (#807) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit * Add tenant dump command * Register tenant schema dump command * Added tests for tenant schema dump command * remove docblocks, fix tenant() logic * trigger ci * Install mysql-client * mysql-client -> mariadb-client * add tenant-schema-test.dump to .gitignore Co-authored-by: Samuel Štancl Co-authored-by: Samuel Štancl --- .gitignore | 1 + Dockerfile | 2 +- src/Commands/TenantDump.php | 54 ++++++++++++++++++++++++++++ src/TenancyServiceProvider.php | 1 + tests/CommandsTest.php | 32 +++++++++++++++++ tests/Etc/tenant-schema.dump | 66 ++++++++++++++++++++++++++++++++++ 6 files changed, 155 insertions(+), 1 deletion(-) create mode 100644 src/Commands/TenantDump.php create mode 100644 tests/Etc/tenant-schema.dump diff --git a/.gitignore b/.gitignore index f470ba75..95522c34 100644 --- a/.gitignore +++ b/.gitignore @@ -8,5 +8,6 @@ psysh phpunit_var_*.xml coverage/ clover.xml +tenant-schema-test.dump tests/Etc/tmp/queuetest.json docker-compose.override.yml diff --git a/Dockerfile b/Dockerfile index 36f52d6a..a636bc45 100644 --- a/Dockerfile +++ b/Dockerfile @@ -24,7 +24,7 @@ ENV LANG=en_GB.UTF-8 # install some OS packages we need RUN apt-get update -RUN apt-get install -y --no-install-recommends libfreetype6-dev libjpeg62-turbo-dev libpng-dev libgmp-dev libldap2-dev netcat curl sqlite3 libsqlite3-dev libpq-dev libzip-dev unzip vim-tiny gosu git +RUN apt-get install -y --no-install-recommends libfreetype6-dev libjpeg62-turbo-dev libpng-dev libgmp-dev libldap2-dev netcat curl mariadb-client sqlite3 libsqlite3-dev libpq-dev libzip-dev unzip vim-tiny gosu git # install php extensions RUN docker-php-ext-configure pgsql -with-pgsql=/usr/local/pgsql \ # && if [ "${PHP_VERSION}" = "7.4" ]; then docker-php-ext-configure gd --with-freetype --with-jpeg; else docker-php-ext-configure gd --with-freetype-dir=/usr/include/ --with-jpeg-dir=/usr/include/; fi \ diff --git a/src/Commands/TenantDump.php b/src/Commands/TenantDump.php new file mode 100644 index 00000000..557c6975 --- /dev/null +++ b/src/Commands/TenantDump.php @@ -0,0 +1,54 @@ +setName('tenants:dump'); + $this->specifyParameters(); + } + + + public function handle(ConnectionResolverInterface $connections, Dispatcher $dispatcher): int + { + $this->tenant()->run(fn() => parent::handle($connections, $dispatcher)); + + return Command::SUCCESS; + } + + public function tenant(): Tenant + { + $tenant = $this->option('tenant') + ?? tenant() + ?? $this->ask('What tenant do you want to dump the schema for?') + ?? tenancy()->query()->first(); + + if (! $tenant instanceof Tenant) { + $tenant = tenancy()->find($tenant); + } + + throw_if(! $tenant, 'Could not identify the tenant to use for dumping the schema.'); + + return $tenant; + } + + protected function getOptions(): array + { + return array_merge([ + ['tenant', null, InputOption::VALUE_OPTIONAL, '', null], + ], parent::getOptions()); + } +} diff --git a/src/TenancyServiceProvider.php b/src/TenancyServiceProvider.php index 4faaccf3..dd061af3 100644 --- a/src/TenancyServiceProvider.php +++ b/src/TenancyServiceProvider.php @@ -88,6 +88,7 @@ class TenancyServiceProvider extends ServiceProvider Commands\Migrate::class, Commands\Rollback::class, Commands\TenantList::class, + Commands\TenantDump::class, Commands\MigrateFresh::class, ]); diff --git a/tests/CommandsTest.php b/tests/CommandsTest.php index d7da0cab..145a93c5 100644 --- a/tests/CommandsTest.php +++ b/tests/CommandsTest.php @@ -91,6 +91,38 @@ class CommandsTest extends TestCase $this->assertTrue(Schema::hasTable('users')); } + /** @test */ + public function migrate_command_loads_schema_state() + { + $tenant = Tenant::create(); + + $this->assertFalse(Schema::hasTable('schema_users')); + $this->assertFalse(Schema::hasTable('users')); + + Artisan::call('tenants:migrate --schema-path="tests/Etc/tenant-schema.dump"'); + + $this->assertFalse(Schema::hasTable('schema_users')); + $this->assertFalse(Schema::hasTable('users')); + + tenancy()->initialize($tenant); + + // Check for both tables to see if missing migrations also get executed + $this->assertTrue(Schema::hasTable('schema_users')); + $this->assertTrue(Schema::hasTable('users')); + } + + /** @test */ + public function dump_command_works() + { + $tenant = Tenant::create(); + Artisan::call('tenants:migrate'); + + tenancy()->initialize($tenant); + + Artisan::call('tenants:dump --path="tests/Etc/tenant-schema-test.dump"'); + $this->assertFileExists('tests/Etc/tenant-schema-test.dump'); + } + /** @test */ public function rollback_command_works() { diff --git a/tests/Etc/tenant-schema.dump b/tests/Etc/tenant-schema.dump new file mode 100644 index 00000000..6af9f019 --- /dev/null +++ b/tests/Etc/tenant-schema.dump @@ -0,0 +1,66 @@ +/*!40103 SET @OLD_TIME_ZONE=@@TIME_ZONE */; +/*!40103 SET TIME_ZONE='+00:00' */; +/*!40014 SET @OLD_UNIQUE_CHECKS=@@UNIQUE_CHECKS, UNIQUE_CHECKS=0 */; +/*!40014 SET @OLD_FOREIGN_KEY_CHECKS=@@FOREIGN_KEY_CHECKS, FOREIGN_KEY_CHECKS=0 */; +/*!40101 SET @OLD_SQL_MODE=@@SQL_MODE, SQL_MODE='NO_AUTO_VALUE_ON_ZERO' */; +/*!40111 SET @OLD_SQL_NOTES=@@SQL_NOTES, SQL_NOTES=0 */; +DROP TABLE IF EXISTS `failed_jobs`; +/*!40101 SET @saved_cs_client = @@character_set_client */; +/*!40101 SET character_set_client = utf8 */; +CREATE TABLE `failed_jobs` ( + `id` bigint(20) unsigned NOT NULL AUTO_INCREMENT, + `uuid` varchar(255) COLLATE utf8mb4_unicode_ci NOT NULL, + `connection` text COLLATE utf8mb4_unicode_ci NOT NULL, + `queue` text COLLATE utf8mb4_unicode_ci NOT NULL, + `payload` longtext COLLATE utf8mb4_unicode_ci NOT NULL, + `exception` longtext COLLATE utf8mb4_unicode_ci NOT NULL, + `failed_at` timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP, + PRIMARY KEY (`id`), + UNIQUE KEY `failed_jobs_uuid_unique` (`uuid`) +) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci; +/*!40101 SET character_set_client = @saved_cs_client */; +DROP TABLE IF EXISTS `migrations`; +/*!40101 SET @saved_cs_client = @@character_set_client */; +/*!40101 SET character_set_client = utf8 */; +CREATE TABLE `migrations` ( + `id` int(10) unsigned NOT NULL AUTO_INCREMENT, + `migration` varchar(255) COLLATE utf8mb4_unicode_ci NOT NULL, + `batch` int(11) NOT NULL, + PRIMARY KEY (`id`) +) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci; +/*!40101 SET character_set_client = @saved_cs_client */; +DROP TABLE IF EXISTS `password_resets`; +/*!40101 SET @saved_cs_client = @@character_set_client */; +/*!40101 SET character_set_client = utf8 */; +CREATE TABLE `password_resets` ( + `email` varchar(255) COLLATE utf8mb4_unicode_ci NOT NULL, + `token` varchar(255) COLLATE utf8mb4_unicode_ci NOT NULL, + `created_at` timestamp NULL DEFAULT NULL, + KEY `password_resets_email_index` (`email`) +) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci; +/*!40101 SET character_set_client = @saved_cs_client */; +DROP TABLE IF EXISTS `users`; +/*!40101 SET @saved_cs_client = @@character_set_client */; +/*!40101 SET character_set_client = utf8 */; +CREATE TABLE `schema_users` ( + `id` bigint(20) unsigned NOT NULL AUTO_INCREMENT, + `name` varchar(255) COLLATE utf8mb4_unicode_ci NOT NULL, + `email` varchar(255) COLLATE utf8mb4_unicode_ci NOT NULL, + `email_verified_at` timestamp NULL DEFAULT NULL, + `password` varchar(255) COLLATE utf8mb4_unicode_ci NOT NULL, + `remember_token` varchar(100) COLLATE utf8mb4_unicode_ci DEFAULT NULL, + `created_at` timestamp NULL DEFAULT NULL, + `updated_at` timestamp NULL DEFAULT NULL, + PRIMARY KEY (`id`), + UNIQUE KEY `users_email_unique` (`email`) +) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci; +/*!40101 SET character_set_client = @saved_cs_client */; +/*!40103 SET TIME_ZONE=@OLD_TIME_ZONE */; + +/*!40101 SET SQL_MODE=@OLD_SQL_MODE */; +/*!40014 SET FOREIGN_KEY_CHECKS=@OLD_FOREIGN_KEY_CHECKS */; +/*!40014 SET UNIQUE_CHECKS=@OLD_UNIQUE_CHECKS */; +/*!40111 SET SQL_NOTES=@OLD_SQL_NOTES */; + +INSERT INTO `migrations` VALUES (2,'2014_10_12_100000_testbench_create_password_resets_table',1); +INSERT INTO `migrations` VALUES (3,'2019_08_19_000000_testbench_create_failed_jobs_table',1);