From a622314437cbeab4f4da5928b8a82fe9934d0ad4 Mon Sep 17 00:00:00 2001 From: Alexis Lefebvre Date: Sun, 5 Nov 2023 16:37:17 +0100 Subject: [PATCH] WIP --- .../DatabaseBackup/AbstractDatabaseBackup.php | 12 ++++-- .../DatabaseBackup/MysqlDatabaseBackup.php | 7 +++- .../DatabaseTools/ORMDatabaseTool.php | 9 +++- tests/App/DataFixtures/ORM/LoadUserData.php | 18 ++++---- tests/Test/ConfigMysqlCacheDbTest.php | 42 +++++++++++++++++++ 5 files changed, 72 insertions(+), 16 deletions(-) diff --git a/src/Services/DatabaseBackup/AbstractDatabaseBackup.php b/src/Services/DatabaseBackup/AbstractDatabaseBackup.php index 6d27a055..e5629e34 100644 --- a/src/Services/DatabaseBackup/AbstractDatabaseBackup.php +++ b/src/Services/DatabaseBackup/AbstractDatabaseBackup.php @@ -13,7 +13,9 @@ namespace Liip\TestFixturesBundle\Services\DatabaseBackup; +use DateTime; use Liip\TestFixturesBundle\Services\FixturesLoaderFactory; +use ReflectionClass; use Symfony\Component\DependencyInjection\ContainerInterface; /** @@ -52,6 +54,8 @@ public function init(array $metadatas, array $classNames, bool $append = false): } else { $this->classNames = $classNames; } + + file_put_contents('/tmp/cache.log', 'init = “'.print_r($this->classNames, true).'”'.PHP_EOL, FILE_APPEND | LOCK_EX); } /** @@ -65,7 +69,7 @@ public function init(array $metadatas, array $classNames, bool $append = false): */ protected function isBackupUpToDate(string $backup): bool { - $backupLastModifiedDateTime = \DateTime::createFromFormat('U', (string) filemtime($backup)); + $backupLastModifiedDateTime = DateTime::createFromFormat('U', (string) filemtime($backup)); $loader = $this->fixturesLoaderFactory->getFixtureLoader($this->classNames); @@ -88,15 +92,15 @@ protected function isBackupUpToDate(string $backup): bool * @param string $class The fully qualified class name of the fixture class to * check modification date on */ - protected function getFixtureLastModified($class): ?\DateTime + protected function getFixtureLastModified($class): ?DateTime { $lastModifiedDateTime = null; - $reflClass = new \ReflectionClass($class); + $reflClass = new ReflectionClass($class); $classFileName = $reflClass->getFileName(); if (file_exists($classFileName)) { - $lastModifiedDateTime = new \DateTime(); + $lastModifiedDateTime = new DateTime(); $lastModifiedDateTime->setTimestamp(filemtime($classFileName)); } diff --git a/src/Services/DatabaseBackup/MysqlDatabaseBackup.php b/src/Services/DatabaseBackup/MysqlDatabaseBackup.php index b3fe6d6b..640144d6 100644 --- a/src/Services/DatabaseBackup/MysqlDatabaseBackup.php +++ b/src/Services/DatabaseBackup/MysqlDatabaseBackup.php @@ -16,6 +16,7 @@ use Doctrine\Common\DataFixtures\Executor\AbstractExecutor; use Doctrine\ORM\EntityManager; use Doctrine\ORM\Tools\SchemaTool; +use function in_array; /** * @author Aleksey Tupichenkov @@ -28,6 +29,8 @@ final class MysqlDatabaseBackup extends AbstractDatabaseBackup public function getBackupFilePath(): string { +// file_put_contents('/tmp/cache.log', 'getBackupFilePath : $this->classNames = “'.print_r($this->classNames, true).'”'.PHP_EOL, FILE_APPEND | LOCK_EX); + return $this->container->getParameter('kernel.cache_dir').'/test_mysql_'.md5(serialize($this->metadatas).serialize($this->classNames)).'.sql'; } @@ -95,7 +98,7 @@ public function restore(AbstractExecutor $executor, array $excludedTables = []): foreach ($this->metadatas as $classMetadata) { $tableName = $classMetadata->table['name']; - if (!\in_array($tableName, $excludedTables, true)) { + if (!in_array($tableName, $excludedTables, true)) { $truncateSql[] = 'DELETE FROM '.$tableName; // in small tables it's really faster than truncate } } @@ -124,6 +127,8 @@ public function restore(AbstractExecutor $executor, array $excludedTables = []): $connection->query('SET FOREIGN_KEY_CHECKS = 1;'); } + file_put_contents('/tmp/cache.log', 'restore unserialize = “'.print_r(unserialize($this->getReferenceBackup()), true).'”'.PHP_EOL, FILE_APPEND | LOCK_EX); + if (self::$metadata) { // it need for better performance foreach (self::$metadata as $class => $data) { diff --git a/src/Services/DatabaseTools/ORMDatabaseTool.php b/src/Services/DatabaseTools/ORMDatabaseTool.php index e30acd4e..0fbc3e50 100644 --- a/src/Services/DatabaseTools/ORMDatabaseTool.php +++ b/src/Services/DatabaseTools/ORMDatabaseTool.php @@ -27,6 +27,8 @@ use Liip\TestFixturesBundle\Event\PreFixtureBackupRestoreEvent; use Liip\TestFixturesBundle\Event\ReferenceSaveEvent; use Liip\TestFixturesBundle\LiipTestFixturesEvents; +use function count; +use function in_array; /** * @author Aleksey Tupichenkov @@ -76,6 +78,9 @@ public function loadFixtures(array $classNames = [], bool $append = false): Abst $backupService = $this->getBackupService(); if ($backupService && $this->databaseCacheEnabled) { + + file_put_contents('/tmp/cache.log', 'loadFixtures if = “'.print_r($classNames, true).'”'.PHP_EOL, FILE_APPEND | LOCK_EX); + $backupService->init($this->getMetadatas(), $classNames, $append); if ($backupService->isBackupActual()) { @@ -103,7 +108,7 @@ public function loadFixtures(array $classNames = [], bool $append = false): Abst // TODO: handle case when using persistent connections. Fail loudly? if (false === $this->getKeepDatabaseAndSchemaParameter()) { $schemaTool = new SchemaTool($this->om); - if (\count($this->excludedDoctrineTables) > 0 || true === $append) { + if (count($this->excludedDoctrineTables) > 0 || true === $append) { if (!empty($this->getMetadatas())) { $schemaTool->updateSchema($this->getMetadatas()); } @@ -179,7 +184,7 @@ protected function createDatabaseIfNotExists(): void $tmpConnection = DriverManager::getConnection($params); $tmpConnection->connect(); - if (!\in_array($dbName, $tmpConnection->getSchemaManager()->listDatabases(), true)) { + if (!in_array($dbName, $tmpConnection->getSchemaManager()->listDatabases(), true)) { $tmpConnection->getSchemaManager()->createDatabase($dbName); } diff --git a/tests/App/DataFixtures/ORM/LoadUserData.php b/tests/App/DataFixtures/ORM/LoadUserData.php index 19b4b652..139aa196 100644 --- a/tests/App/DataFixtures/ORM/LoadUserData.php +++ b/tests/App/DataFixtures/ORM/LoadUserData.php @@ -24,21 +24,21 @@ class LoadUserData extends AbstractFixture */ public function load(ObjectManager $manager): void { - $user = new User(); - $user->setId(1); - $user->setName('foo bar'); - $user->setEmail('foo@bar.com'); + $user1 = new User(); + $user1->setId(1); + $user1->setName('foo bar'); + $user1->setEmail('foo@bar.com'); - $manager->persist($user); + $manager->persist($user1); $manager->flush(); - $this->addReference('user', $user); + $this->addReference('user', $user1); - $user = clone $this->getReference('user'); + $user2 = clone $user1; - $user->setId(2); + $user2->setId(2); - $manager->persist($user); + $manager->persist($user2); $manager->flush(); } } diff --git a/tests/Test/ConfigMysqlCacheDbTest.php b/tests/Test/ConfigMysqlCacheDbTest.php index 257701a0..94efe33c 100644 --- a/tests/Test/ConfigMysqlCacheDbTest.php +++ b/tests/Test/ConfigMysqlCacheDbTest.php @@ -16,6 +16,7 @@ use Doctrine\Common\Annotations\Annotation\IgnoreAnnotation; use Liip\Acme\Tests\App\Entity\User; use Liip\Acme\Tests\AppConfigMysqlCacheDb\AppConfigMysqlKernelCacheDb; +use Liip\TestFixturesBundle\Services\DatabaseBackup\MysqlDatabaseBackup; /** * Test MySQL database with database caching enabled. @@ -119,15 +120,28 @@ public function testLoadFixturesAndCheckBackup(): void */ public function testLoadFixturesCheckReferences(): void { + $this->databaseTool->setDatabaseCacheEnabled(true); + + file_put_contents('/tmp/cache.log', '',LOCK_EX); + $referenceRepository = $this->databaseTool->loadFixtures([ 'Liip\Acme\Tests\App\DataFixtures\ORM\LoadUserData', ])->getReferenceRepository(); + // Check that 2 users have been loaded in the database + $this->assertCount( + 2, + $this->userRepository->findAll() + ); + $references = (method_exists($referenceRepository, 'getReferencesByClass')) // with getReferencesByClass(), references are grouped by class ? $referenceRepository->getReferencesByClass()['Liip\Acme\Tests\App\Entity\User'] : $referenceRepository->getReferences(); + file_put_contents('/tmp/cache.log', '$references 1 = “'.print_r(array_keys($references), true).'”'.PHP_EOL, FILE_APPEND | LOCK_EX); + + $this->assertArrayHasKey('user', $references); $this->assertCount(1, $references); $referenceRepository = $this->databaseTool->loadFixtures([ @@ -135,11 +149,39 @@ public function testLoadFixturesCheckReferences(): void 'Liip\Acme\Tests\App\DataFixtures\ORM\LoadSecondUserData', ])->getReferenceRepository(); + // Check that 3 users have been loaded in the database + $this->assertCount( + 3, + $this->userRepository->findAll() + ); + + $sqliteDatabaseBackup = $this->getTestContainer()->get(MysqlDatabaseBackup::class); + + $this->assertInstanceOf(MysqlDatabaseBackup::class, $sqliteDatabaseBackup); + + $referenceBackupFilePath = $sqliteDatabaseBackup->getReferenceBackupFilePath(); + + if (!is_file($referenceBackupFilePath)) { + $this->fail($referenceBackupFilePath.' is not a file.'); + } + + $referenceData = unserialize(file_get_contents($referenceBackupFilePath)); + + file_put_contents('/tmp/cache.log', '$referenceData = “'.print_r($referenceData, true).'”'.PHP_EOL, FILE_APPEND | LOCK_EX); + + // check that the cache file contains these 2 references + $this->assertArrayHasKey('user', $referenceData['references']); + $this->assertArrayHasKey('user-second', $referenceData['references']); + $references = (method_exists($referenceRepository, 'getReferencesByClass')) // with getReferencesByClass(), references are grouped by class ? $referenceRepository->getReferencesByClass()['Liip\Acme\Tests\App\Entity\User'] : $referenceRepository->getReferences(); +// file_put_contents('/tmp/cache.log', '$references 2 = “'.print_r(array_keys($references), true).'”'.PHP_EOL, FILE_APPEND | LOCK_EX); + + $this->assertArrayHasKey('user', $references); + $this->assertArrayHasKey('user-second', $references); $this->assertCount(2, $references); }