diff --git a/bin/doctrine-migrations.php b/bin/doctrine-migrations.php index e106154cea..8e2371b02c 100644 --- a/bin/doctrine-migrations.php +++ b/bin/doctrine-migrations.php @@ -6,16 +6,11 @@ use Doctrine\Migrations\Tools\Console\ConsoleRunner; use Phar; -use Symfony\Component\Console\Helper\HelperSet; -use Symfony\Component\Console\Helper\QuestionHelper; -use const DIRECTORY_SEPARATOR; -use const E_USER_ERROR; use const PHP_EOL; +use const STDERR; use function extension_loaded; use function file_exists; -use function getcwd; -use function is_readable; -use function trigger_error; +use function fwrite; (static function () : void { $autoloadFiles = [ @@ -24,7 +19,6 @@ ]; $autoloaderFound = false; - foreach ($autoloadFiles as $autoloadFile) { if (! file_exists($autoloadFile)) { continue; @@ -36,57 +30,15 @@ if (! $autoloaderFound) { if (extension_loaded('phar') && Phar::running() !== '') { - echo 'The PHAR was built without dependencies!' . PHP_EOL; + fwrite(STDERR, 'The PHAR was built without dependencies!' . PHP_EOL); exit(1); } - echo 'vendor/autoload.php could not be found. Did you run `composer install`?', PHP_EOL; + fwrite(STDERR, 'vendor/autoload.php could not be found. Did you run `composer install`?' . PHP_EOL); exit(1); } - // Support for using the Doctrine ORM convention of providing a `cli-config.php` file. - $configurationDirectories = [ - getcwd(), - getcwd() . DIRECTORY_SEPARATOR . 'config', - ]; - - $configurationFile = null; - foreach ($configurationDirectories as $configurationDirectory) { - $configurationFilePath = $configurationDirectory . DIRECTORY_SEPARATOR . 'cli-config.php'; - - if (! file_exists($configurationFilePath)) { - continue; - } - - $configurationFile = $configurationFilePath; - break; - } - - $helperSet = null; - if ($configurationFile !== null) { - if (! is_readable($configurationFile)) { - trigger_error('Configuration file [' . $configurationFile . '] does not have read permission.', E_USER_ERROR); - exit(1); - } - - $helperSet = require $configurationFile; - - if (! $helperSet instanceof HelperSet) { - foreach ($GLOBALS as $helperSetCandidate) { - if (! $helperSetCandidate instanceof HelperSet) { - continue; - } - - $helperSet = $helperSetCandidate; - break; - } - } - } - - $helperSet = $helperSet ?? new HelperSet(); - $helperSet->set(new QuestionHelper(), 'question'); - - $commands = []; + $dependencyFactory = ConsoleRunner::findDependencyFactory(); - ConsoleRunner::run($helperSet, $commands); + ConsoleRunner::run([], $dependencyFactory); })(); diff --git a/docs/en/reference/configuration.rst b/docs/en/reference/configuration.rst index 34cdd5f98f..63c99fd852 100644 --- a/docs/en/reference/configuration.rst +++ b/docs/en/reference/configuration.rst @@ -139,6 +139,7 @@ Here are details about what each configuration option does: Here the possible options for ``table_storage``: + +----------------------------+------------+------------------------------+----------------------------------------------------------------------------------+ | Name | Required | Default | Description | +============================+============+==============================+==================================================================================+ @@ -262,6 +263,23 @@ the following command: $ mysqladmin create migrations_docs_example + +If you have already a DBAL connection available in your application, ``migrations-db.php`` can return it directly: + +.. code-block:: php + + 'migrations_docs_example', + 'user' => 'root', + 'password' => '', + 'host' => 'localhost', + 'driver' => 'pdo_mysql', + ]); + + Advanced ~~~~~~~~ @@ -279,16 +297,16 @@ out of the root of your project. require 'vendor/autoload.php'; use Doctrine\DBAL\DriverManager; - use Doctrine\DBAL\Tools\Console\Helper\ConnectionHelper; - use Symfony\Component\Console\Helper\HelperSet; + use Doctrine\Migrations\Configuration\Configuration\PhpFile; + use Doctrine\Migrations\Configuration\Connection\ExistingConnection; + use Doctrine\Migrations\DependencyFactory; - $dbParams = include 'migrations-db.php'; + $config = new PhpFile('migrations.php'); // Or use one of the Doctrine\Migrations\Configuration\Configuration\* loaders - $connection = DriverManager::getConnection($dbParams); + $conn = DriverManager::getConnection(['driver' => 'pdo_sqlite', 'memory' => true]); + + return DependencyFactory::fromConnection($config, new ExistingConnection($conn)); - return new HelperSet([ - 'db' => new ConnectionHelper($connection), - ]); The above setup assumes you are not using the ORM. If you want to use the ORM, first require it in your project with composer: @@ -305,24 +323,20 @@ Now update your ``cli-config.php`` in the root of your project to look like the require 'vendor/autoload.php'; - use Doctrine\DBAL\Tools\Console\Helper\ConnectionHelper; - use Doctrine\ORM\Tools\Console\Helper\EntityManagerHelper; - use Doctrine\ORM\Tools\Setup; use Doctrine\ORM\EntityManager; - use Symfony\Component\Console\Helper\HelperSet; + use Doctrine\ORM\Tools\Setup; + use Doctrine\Migrations\Configuration\EntityManager\ExistingEntityManager; + use Doctrine\Migrations\DependencyFactory; + + $config = new PhpFile('migrations.php'); // Or use one of the Doctrine\Migrations\Configuration\Configuration\* loaders $paths = [__DIR__.'/lib/MyProject/Entities']; $isDevMode = true; - $dbParams = include 'migrations-db.php'; - $config = Setup::createAnnotationMetadataConfiguration($paths, $isDevMode); - $entityManager = EntityManager::create($dbParams, $config); + $entityManager = EntityManager::create(['driver' => 'pdo_sqlite', 'memory' => true], $config); - return new HelperSet([ - 'em' => new EntityManagerHelper($entityManager), - 'db' => new ConnectionHelper($entityManager->getConnection()), - ]); + return DependencyFactory::fromEntityManager($config, new ExistingEntityManager($entityManager)); Make sure to create the directory where your ORM entities will be located: diff --git a/docs/en/reference/custom-configuration.rst b/docs/en/reference/custom-configuration.rst index 069854b4d9..20098a2f81 100644 --- a/docs/en/reference/custom-configuration.rst +++ b/docs/en/reference/custom-configuration.rst @@ -14,14 +14,13 @@ Once you have your custom integration setup, you can modify it to look like the require_once __DIR__.'/vendor/autoload.php'; use Doctrine\DBAL\DriverManager; - use Doctrine\DBAL\Tools\Console\Helper\ConnectionHelper; use Doctrine\Migrations\Configuration\Configuration; + use Doctrine\Migrations\Configuration\Connection\ExistingConnection; + use Doctrine\Migrations\Configuration\Configuration\ExistingConfiguration; + use Doctrine\Migrations\DependencyFactory; une Doctrine\Migrations\Metadata\Storage\TableMetadataStorageConfiguration; use Doctrine\Migrations\Tools\Console\Command; - use Doctrine\Migrations\Tools\Console\Helper\ConfigurationHelper; use Symfony\Component\Console\Application; - use Symfony\Component\Console\Helper\HelperSet; - use Symfony\Component\Console\Helper\QuestionHelper; $dbParams = [ 'dbname' => 'migrations_docs_example', @@ -45,24 +44,23 @@ Once you have your custom integration setup, you can modify it to look like the $configuration->setMetadataStorageConfiguration($storageConfiguration); - $helperSet = new HelperSet(); - $helperSet->set(new QuestionHelper(), 'question'); - $helperSet->set(new ConnectionHelper($connection), 'db'); - $helperSet->set(new ConfigurationHelper($connection, $configuration)); + $dependencyFactory = DependencyFactory::fromConnection( + new ExistingConfiguration($configuration), + new ExistingConnection($connection) + ); $cli = new Application('Doctrine Migrations'); $cli->setCatchExceptions(true); - $cli->setHelperSet($helperSet); $cli->addCommands(array( - new Command\DumpSchemaCommand(), - new Command\ExecuteCommand(), - new Command\GenerateCommand(), - new Command\LatestCommand(), - new Command\MigrateCommand(), - new Command\RollupCommand(), - new Command\StatusCommand(), - new Command\VersionCommand() + new Command\DumpSchemaCommand($dependencyFactory), + new Command\ExecuteCommand($dependencyFactory), + new Command\GenerateCommand($dependencyFactory), + new Command\LatestCommand($dependencyFactory), + new Command\MigrateCommand($dependencyFactory), + new Command\RollupCommand($dependencyFactory), + new Command\StatusCommand($dependencyFactory), + new Command\VersionCommand($dependencyFactory) )); $cli->run(); diff --git a/docs/en/reference/custom-integration.rst b/docs/en/reference/custom-integration.rst index 444aa63094..5e02ddb937 100644 --- a/docs/en/reference/custom-integration.rst +++ b/docs/en/reference/custom-integration.rst @@ -20,14 +20,14 @@ Now place the following code in the ``migrations`` file: require_once __DIR__.'/vendor/autoload.php'; use Doctrine\DBAL\DriverManager; - use Doctrine\DBAL\Tools\Console\Helper\ConnectionHelper; + use Doctrine\Migrations\DependencyFactory; + use Doctrine\Migrations\Configuration\Configuration\PhpFile; + use Doctrine\Migrations\Configuration\Connection\ExistingConnection; use Doctrine\Migrations\Tools\Console\Command; use Symfony\Component\Console\Application; - use Symfony\Component\Console\Helper\HelperSet; - use Symfony\Component\Console\Helper\QuestionHelper; $dbParams = [ - 'dbname' => 'migrations_test', + 'dbname' => 'migrations_docs_example', 'user' => 'root', 'password' => '', 'host' => 'localhost', @@ -36,27 +36,27 @@ Now place the following code in the ``migrations`` file: $connection = DriverManager::getConnection($dbParams); - $helperSet = new HelperSet(); - $helperSet->set(new QuestionHelper(), 'question'); - $helperSet->set(new ConnectionHelper($connection), 'db'); + $config = new PhpFile('migrations.php'); // Or use one of the Doctrine\Migrations\Configuration\Configuration\* loaders + + $dependencyFactory = DependencyFactory::fromConnection($config, new ExistingConnection($conn)); $cli = new Application('Doctrine Migrations'); $cli->setCatchExceptions(true); - $cli->setHelperSet($helperSet); $cli->addCommands(array( - new Command\DumpSchemaCommand(), - new Command\ExecuteCommand(), - new Command\GenerateCommand(), - new Command\LatestCommand(), - new Command\MigrateCommand(), - new Command\RollupCommand(), - new Command\StatusCommand(), - new Command\VersionCommand() + new Command\DumpSchemaCommand($dependencyFactory), + new Command\ExecuteCommand($dependencyFactory), + new Command\GenerateCommand($dependencyFactory), + new Command\LatestCommand($dependencyFactory), + new Command\MigrateCommand($dependencyFactory), + new Command\RollupCommand($dependencyFactory), + new Command\StatusCommand($dependencyFactory), + new Command\VersionCommand($dependencyFactory) )); $cli->run(); + Now you can execute the migrations console application like this: .. code-block:: bash diff --git a/lib/Doctrine/Migrations/Configuration/Loader/ArrayLoader.php b/lib/Doctrine/Migrations/Configuration/Configuration/ConfigurationArray.php similarity index 87% rename from lib/Doctrine/Migrations/Configuration/Loader/ArrayLoader.php rename to lib/Doctrine/Migrations/Configuration/Configuration/ConfigurationArray.php index c7970fcec6..441e8cc3f2 100644 --- a/lib/Doctrine/Migrations/Configuration/Loader/ArrayLoader.php +++ b/lib/Doctrine/Migrations/Configuration/Configuration/ConfigurationArray.php @@ -2,12 +2,11 @@ declare(strict_types=1); -namespace Doctrine\Migrations\Configuration\Loader; +namespace Doctrine\Migrations\Configuration\Configuration; use Closure; use Doctrine\Migrations\Configuration\Configuration; -use Doctrine\Migrations\Configuration\Exception\InvalidConfigurationKey; -use Doctrine\Migrations\Configuration\Exception\UnableToLoadResource; +use Doctrine\Migrations\Configuration\Configuration\Exception\InvalidConfigurationKey; use Doctrine\Migrations\Metadata\Storage\TableMetadataStorageConfiguration; use Doctrine\Migrations\Tools\BooleanStringFormatter; use function assert; @@ -16,20 +15,21 @@ use function is_bool; use function is_callable; -/** - * @internal - */ -final class ArrayLoader implements Loader +final class ConfigurationArray implements ConfigurationLoader { + /** @var array */ + private $configurations; + /** - * @param mixed $array + * @param array $configurations */ - public function load($array) : Configuration + public function __construct(array $configurations) { - if (! is_array($array)) { - throw UnableToLoadResource::with(static::class); - } + $this->configurations = $configurations; + } + public function getConfiguration() : Configuration + { $configMap = [ 'migrations_paths' => static function ($paths, Configuration $configuration) : void { foreach ($paths as $namespace => $path) { @@ -63,7 +63,7 @@ public function load($array) : Configuration ]; $object = new Configuration(); - self::applyConfigs($configMap, $object, $array); + self::applyConfigs($configMap, $object, $this->configurations); if ($object->getMetadataStorageConfiguration() === null) { $object->setMetadataStorageConfiguration(new TableMetadataStorageConfiguration()); diff --git a/lib/Doctrine/Migrations/Configuration/Configuration/ConfigurationFile.php b/lib/Doctrine/Migrations/Configuration/Configuration/ConfigurationFile.php new file mode 100644 index 0000000000..feeb9518a0 --- /dev/null +++ b/lib/Doctrine/Migrations/Configuration/Configuration/ConfigurationFile.php @@ -0,0 +1,35 @@ +file = $file; + } + + /** + * @param array $directories + * + * @return array + */ + final protected function getDirectoriesRelativeToFile(array $directories, string $file) : array + { + foreach ($directories as $ns => $dir) { + $path = realpath(dirname($file) . '/' . $dir); + + $directories[$ns] = $path !== false ? $path : $dir; + } + + return $directories; + } +} diff --git a/lib/Doctrine/Migrations/Configuration/Configuration/ConfigurationFileWithFallback.php b/lib/Doctrine/Migrations/Configuration/Configuration/ConfigurationFileWithFallback.php new file mode 100644 index 0000000000..7ba4a6344c --- /dev/null +++ b/lib/Doctrine/Migrations/Configuration/Configuration/ConfigurationFileWithFallback.php @@ -0,0 +1,66 @@ +file = $file; + } + + public function getConfiguration() : Configuration + { + if ($this->file !== null) { + return $this->loadConfiguration($this->file); + } + + /** + * If no config has been provided, look for default config file in the path. + */ + $defaultFiles = [ + 'migrations.xml', + 'migrations.yml', + 'migrations.yaml', + 'migrations.json', + 'migrations.php', + ]; + + foreach ($defaultFiles as $file) { + if ($this->configurationFileExists($file)) { + return $this->loadConfiguration($file); + } + } + + throw MissingConfigurationFile::new(); + } + + private function configurationFileExists(string $config) : bool + { + return file_exists($config); + } + + /** + * @throws FileTypeNotSupported + */ + private function loadConfiguration(string $file) : Configuration + { + return (new FormattedFile($file))->getConfiguration(); + } +} diff --git a/lib/Doctrine/Migrations/Configuration/Configuration/ConfigurationLoader.php b/lib/Doctrine/Migrations/Configuration/Configuration/ConfigurationLoader.php new file mode 100644 index 0000000000..680e603465 --- /dev/null +++ b/lib/Doctrine/Migrations/Configuration/Configuration/ConfigurationLoader.php @@ -0,0 +1,12 @@ +configurations = $configurations; + } + + public function getConfiguration() : Configuration + { + return $this->configurations; + } +} diff --git a/lib/Doctrine/Migrations/Configuration/Configuration/FormattedFile.php b/lib/Doctrine/Migrations/Configuration/Configuration/FormattedFile.php new file mode 100644 index 0000000000..e01fa12f43 --- /dev/null +++ b/lib/Doctrine/Migrations/Configuration/Configuration/FormattedFile.php @@ -0,0 +1,54 @@ +loaders = [ + 'json' => static function ($file) : ConfigurationLoader { + return new JsonFile($file); + }, + 'php' => static function ($file) : ConfigurationLoader { + return new PhpFile($file); + }, + 'xml' => static function ($file) : ConfigurationLoader { + return new XmlFile($file); + }, + 'yaml' => static function ($file) : ConfigurationLoader { + return new YamlFile($file); + }, + 'yml' => static function ($file) : ConfigurationLoader { + return new YamlFile($file); + }, + ]; + } + + public function getConfiguration() : Configuration + { + if (count($this->loaders) === 0) { + $this->setDefaultLoaders(); + } + + $extension = pathinfo($this->file, PATHINFO_EXTENSION); + if (! isset($this->loaders[$extension])) { + throw Configuration\Exception\InvalidConfigurationFormat::new($this->file); + } + + return $this->loaders[$extension]($this->file)->getConfiguration(); + } +} diff --git a/lib/Doctrine/Migrations/Configuration/Configuration/JsonFile.php b/lib/Doctrine/Migrations/Configuration/Configuration/JsonFile.php new file mode 100644 index 0000000000..c17a0df1fb --- /dev/null +++ b/lib/Doctrine/Migrations/Configuration/Configuration/JsonFile.php @@ -0,0 +1,44 @@ +file)) { + throw FileNotFound::new($this->file); + } + + $contents = file_get_contents($this->file); + + assert($contents !== false); + + $config = json_decode($contents, true); + + if (json_last_error() !== JSON_ERROR_NONE) { + throw JsonNotValid::new(); + } + + if (isset($config['migrations_paths'])) { + $config['migrations_paths'] = $this->getDirectoriesRelativeToFile( + $config['migrations_paths'], + $this->file + ); + } + + return (new ConfigurationArray($config))->getConfiguration(); + } +} diff --git a/lib/Doctrine/Migrations/Configuration/Configuration/PhpFile.php b/lib/Doctrine/Migrations/Configuration/Configuration/PhpFile.php new file mode 100644 index 0000000000..f9ae812a6b --- /dev/null +++ b/lib/Doctrine/Migrations/Configuration/Configuration/PhpFile.php @@ -0,0 +1,35 @@ +file)) { + throw FileNotFound::new($this->file); + } + $config = require $this->file; + if ($config instanceof Configuration) { + return $config; + } + + assert(is_array($config)); + if (isset($config['migrations_paths'])) { + $config['migrations_paths'] = $this->getDirectoriesRelativeToFile( + $config['migrations_paths'], + $this->file + ); + } + + return (new ConfigurationArray($config))->getConfiguration(); + } +} diff --git a/lib/Doctrine/Migrations/Configuration/Loader/XML/configuration.xsd b/lib/Doctrine/Migrations/Configuration/Configuration/XML/configuration.xsd similarity index 100% rename from lib/Doctrine/Migrations/Configuration/Loader/XML/configuration.xsd rename to lib/Doctrine/Migrations/Configuration/Configuration/XML/configuration.xsd diff --git a/lib/Doctrine/Migrations/Configuration/Loader/XmlFileLoader.php b/lib/Doctrine/Migrations/Configuration/Configuration/XmlFile.php similarity index 79% rename from lib/Doctrine/Migrations/Configuration/Loader/XmlFileLoader.php rename to lib/Doctrine/Migrations/Configuration/Configuration/XmlFile.php index dabcf03f60..6bb9962098 100644 --- a/lib/Doctrine/Migrations/Configuration/Loader/XmlFileLoader.php +++ b/lib/Doctrine/Migrations/Configuration/Configuration/XmlFile.php @@ -2,11 +2,11 @@ declare(strict_types=1); -namespace Doctrine\Migrations\Configuration\Loader; +namespace Doctrine\Migrations\Configuration\Configuration; use Doctrine\Migrations\Configuration\Configuration; +use Doctrine\Migrations\Configuration\Configuration\Exception\XmlNotValid; use Doctrine\Migrations\Configuration\Exception\FileNotFound; -use Doctrine\Migrations\Configuration\Exception\XmlNotValid; use Doctrine\Migrations\Tools\BooleanStringFormatter; use DOMDocument; use SimpleXMLElement; @@ -20,31 +20,17 @@ use function simplexml_load_string; use function strtr; -/** - * @internal - */ -final class XmlFileLoader extends AbstractFileLoader +final class XmlFile extends ConfigurationFile { - /** @var ArrayLoader */ - private $arrayLoader; - - public function __construct() - { - $this->arrayLoader = new ArrayLoader(); - } - - /** - * @param mixed|string $file - */ - public function load($file) : Configuration + public function getConfiguration() : Configuration { - if (! file_exists($file)) { - throw FileNotFound::new(); + if (! file_exists($this->file)) { + throw FileNotFound::new($this->file); } - $this->validateXml($file); + $this->validateXml($this->file); - $rawXML = file_get_contents($file); + $rawXML = file_get_contents($this->file); assert($rawXML !== false); $root = simplexml_load_string($rawXML, SimpleXMLElement::class, LIBXML_NOCDATA); @@ -59,13 +45,13 @@ public function load($file) : Configuration ); } if (isset($config['migrations_paths'])) { - $config['migrations_paths'] = $this->getDirectoryRelativeToFile( - $file, - $config['migrations_paths'] + $config['migrations_paths'] = $this->getDirectoriesRelativeToFile( + $config['migrations_paths'], + $this->file ); } - return $this->arrayLoader->load($config); + return (new ConfigurationArray($config))->getConfiguration(); } /** diff --git a/lib/Doctrine/Migrations/Configuration/Loader/YamlFileLoader.php b/lib/Doctrine/Migrations/Configuration/Configuration/YamlFile.php similarity index 51% rename from lib/Doctrine/Migrations/Configuration/Loader/YamlFileLoader.php rename to lib/Doctrine/Migrations/Configuration/Configuration/YamlFile.php index b75e64c340..e28a604c24 100644 --- a/lib/Doctrine/Migrations/Configuration/Loader/YamlFileLoader.php +++ b/lib/Doctrine/Migrations/Configuration/Configuration/YamlFile.php @@ -2,12 +2,12 @@ declare(strict_types=1); -namespace Doctrine\Migrations\Configuration\Loader; +namespace Doctrine\Migrations\Configuration\Configuration; use Doctrine\Migrations\Configuration\Configuration; +use Doctrine\Migrations\Configuration\Configuration\Exception\YamlNotAvailable; +use Doctrine\Migrations\Configuration\Configuration\Exception\YamlNotValid; use Doctrine\Migrations\Configuration\Exception\FileNotFound; -use Doctrine\Migrations\Configuration\Exception\YamlNotAvailable; -use Doctrine\Migrations\Configuration\Exception\YamlNotValid; use Symfony\Component\Yaml\Exception\ParseException; use Symfony\Component\Yaml\Yaml; use function assert; @@ -16,33 +16,19 @@ use function file_get_contents; use function is_array; -/** - * @internal - */ -final class YamlFileLoader extends AbstractFileLoader +final class YamlFile extends ConfigurationFile { - /** @var ArrayLoader */ - private $arrayLoader; - - public function __construct() - { - $this->arrayLoader = new ArrayLoader(); - } - - /** - * @param mixed $file - */ - public function load($file) : Configuration + public function getConfiguration() : Configuration { if (! class_exists(Yaml::class)) { throw YamlNotAvailable::new(); } - if (! file_exists($file)) { - throw FileNotFound::new(); + if (! file_exists($this->file)) { + throw FileNotFound::new($this->file); } - $content = file_get_contents($file); + $content = file_get_contents($this->file); assert($content !== false); @@ -57,12 +43,12 @@ public function load($file) : Configuration } if (isset($config['migrations_paths'])) { - $config['migrations_paths'] = $this->getDirectoryRelativeToFile( - $file, - $config['migrations_paths'] + $config['migrations_paths'] = $this->getDirectoriesRelativeToFile( + $config['migrations_paths'], + $this->file ); } - return $this->arrayLoader->load($config); + return (new ConfigurationArray($config))->getConfiguration(); } } diff --git a/lib/Doctrine/Migrations/Configuration/ConfigurationLoader.php b/lib/Doctrine/Migrations/Configuration/ConfigurationLoader.php deleted file mode 100644 index 0e15127df4..0000000000 --- a/lib/Doctrine/Migrations/Configuration/ConfigurationLoader.php +++ /dev/null @@ -1,53 +0,0 @@ -loaders[$type] = $loader; - } - - private function setDefaultLoaders() : void - { - $this->loaders = [ - 'array' => new ArrayLoader(), - 'json' => new JsonFileLoader(), - 'php' => new PhpFileLoader(), - 'xml' => new XmlFileLoader(), - 'yaml' => new YamlFileLoader(), - 'yml' => new YamlFileLoader(), - ]; - } - - public function getLoader(string $type) : Loader - { - if (count($this->loaders) === 0) { - $this->setDefaultLoaders(); - } - - if (! isset($this->loaders[$type])) { - throw UnknownLoader::new($type); - } - - return $this->loaders[$type]; - } -} diff --git a/lib/Doctrine/Migrations/Configuration/Connection/ConfigurationFile.php b/lib/Doctrine/Migrations/Configuration/Connection/ConfigurationFile.php new file mode 100644 index 0000000000..d53c25e4ed --- /dev/null +++ b/lib/Doctrine/Migrations/Configuration/Connection/ConfigurationFile.php @@ -0,0 +1,48 @@ +filename = $filename; + } + + public function getConnection() : Connection + { + if (! file_exists($this->filename)) { + throw FileNotFound::new($this->filename); + } + + $params = include $this->filename; + + if ($params instanceof Connection) { + return $params; + } + + if ($params instanceof ConnectionLoader) { + return $params->getConnection(); + } + + if (is_array($params)) { + return DriverManager::getConnection($params); + } + throw InvalidConfiguration::invalidArrayConfiguration(); + } +} diff --git a/lib/Doctrine/Migrations/Configuration/Connection/ConnectionLoader.php b/lib/Doctrine/Migrations/Configuration/Connection/ConnectionLoader.php index e1699a0ea7..6d28362f1f 100644 --- a/lib/Doctrine/Migrations/Configuration/Connection/ConnectionLoader.php +++ b/lib/Doctrine/Migrations/Configuration/Connection/ConnectionLoader.php @@ -5,7 +5,7 @@ namespace Doctrine\Migrations\Configuration\Connection; use Doctrine\DBAL\Connection; -use Doctrine\Migrations\Tools\Console\Exception\ConnectionNotSpecified; +use Doctrine\Migrations\Configuration\Connection\Exception\ConnectionNotSpecified; /** * The ConnectionLoader defines the interface used to load the Doctrine\DBAL\Connection instance to use diff --git a/lib/Doctrine/Migrations/Tools/Console/Exception/ConnectionNotSpecified.php b/lib/Doctrine/Migrations/Configuration/Connection/Exception/ConnectionNotSpecified.php similarity index 78% rename from lib/Doctrine/Migrations/Tools/Console/Exception/ConnectionNotSpecified.php rename to lib/Doctrine/Migrations/Configuration/Connection/Exception/ConnectionNotSpecified.php index 098c841efc..71068e1c91 100644 --- a/lib/Doctrine/Migrations/Tools/Console/Exception/ConnectionNotSpecified.php +++ b/lib/Doctrine/Migrations/Configuration/Connection/Exception/ConnectionNotSpecified.php @@ -2,11 +2,11 @@ declare(strict_types=1); -namespace Doctrine\Migrations\Tools\Console\Exception; +namespace Doctrine\Migrations\Configuration\Connection\Exception; use InvalidArgumentException; -final class ConnectionNotSpecified extends InvalidArgumentException implements ConsoleException +final class ConnectionNotSpecified extends InvalidArgumentException implements LoaderException { public static function new() : self { diff --git a/lib/Doctrine/Migrations/Configuration/Connection/Exception/FileNotFound.php b/lib/Doctrine/Migrations/Configuration/Connection/Exception/FileNotFound.php new file mode 100644 index 0000000000..f3b716af80 --- /dev/null +++ b/lib/Doctrine/Migrations/Configuration/Connection/Exception/FileNotFound.php @@ -0,0 +1,16 @@ +connection = $connection; + } + + public function getConnection() : Connection + { + return $this->connection; + } +} diff --git a/lib/Doctrine/Migrations/Configuration/Connection/Loader/ArrayConnectionConfigurationLoader.php b/lib/Doctrine/Migrations/Configuration/Connection/Loader/ArrayConnectionConfigurationLoader.php deleted file mode 100644 index 79cfb65625..0000000000 --- a/lib/Doctrine/Migrations/Configuration/Connection/Loader/ArrayConnectionConfigurationLoader.php +++ /dev/null @@ -1,58 +0,0 @@ -filename = $filename; - $this->fallback = $fallback; - } - - /** - * Read the input and return a Configuration, returns null if the config - * is not supported. - * - * @throws InvalidConfiguration - */ - public function getConnection() : Connection - { - if ($this->filename === null) { - return $this->fallback->getConnection(); - } - - if (! file_exists($this->filename)) { - return $this->fallback->getConnection(); - } - - $params = include $this->filename; - - if (! is_array($params)) { - throw InvalidConfiguration::invalidArrayConfiguration(); - } - - return DriverManager::getConnection($params); - } -} diff --git a/lib/Doctrine/Migrations/Configuration/Connection/Loader/ConnectionHelperLoader.php b/lib/Doctrine/Migrations/Configuration/Connection/Loader/ConnectionHelperLoader.php deleted file mode 100644 index 82073afca5..0000000000 --- a/lib/Doctrine/Migrations/Configuration/Connection/Loader/ConnectionHelperLoader.php +++ /dev/null @@ -1,51 +0,0 @@ -helperSet = $helperSet ?: new HelperSet(); - $this->helperName = $helperName; - $this->fallback = $fallback; - } - - /** - * Read the input and return a Configuration, returns null if the config - * is not supported. - */ - public function getConnection() : Connection - { - if ($this->helperSet->has($this->helperName)) { - $connectionHelper = $this->helperSet->get($this->helperName); - - if ($connectionHelper instanceof ConnectionHelper) { - return $connectionHelper->getConnection(); - } - } - - return $this->fallback->getConnection(); - } -} diff --git a/lib/Doctrine/Migrations/Configuration/Connection/Loader/NoConnectionLoader.php b/lib/Doctrine/Migrations/Configuration/Connection/Loader/NoConnectionLoader.php deleted file mode 100644 index bcc57f9299..0000000000 --- a/lib/Doctrine/Migrations/Configuration/Connection/Loader/NoConnectionLoader.php +++ /dev/null @@ -1,20 +0,0 @@ -filename = $filename; + } + + /** + * Read the input and return a Configuration, returns null if the config + * is not supported. + * + * @throws InvalidConfiguration + */ + public function getEntityManager() : EntityManagerInterface + { + if (! file_exists($this->filename)) { + throw FileNotFound::new($this->filename); + } + + $params = include $this->filename; + + if ($params instanceof EntityManagerInterface) { + return $params; + } + + if ($params instanceof EntityManagerLoader) { + return $params->getEntityManager(); + } + + throw InvalidConfiguration::invalidArrayConfiguration(); + } +} diff --git a/lib/Doctrine/Migrations/Configuration/EntityManager/EntityManagerLoader.php b/lib/Doctrine/Migrations/Configuration/EntityManager/EntityManagerLoader.php new file mode 100644 index 0000000000..e2437a78cd --- /dev/null +++ b/lib/Doctrine/Migrations/Configuration/EntityManager/EntityManagerLoader.php @@ -0,0 +1,18 @@ +entityManager = $entityManager; + } + + public function getEntityManager() : EntityManagerInterface + { + return $this->entityManager; + } +} diff --git a/lib/Doctrine/Migrations/Configuration/Exception/FileNotFound.php b/lib/Doctrine/Migrations/Configuration/Exception/FileNotFound.php index 1577f1051c..cda795679d 100644 --- a/lib/Doctrine/Migrations/Configuration/Exception/FileNotFound.php +++ b/lib/Doctrine/Migrations/Configuration/Exception/FileNotFound.php @@ -5,11 +5,12 @@ namespace Doctrine\Migrations\Configuration\Exception; use InvalidArgumentException; +use function sprintf; final class FileNotFound extends InvalidArgumentException implements ConfigurationException { - public static function new() : self + public static function new(string $file) : self { - return new self('Given config file does not exist'); + return new self(sprintf('The "%s" configuration file does not exist.', $file)); } } diff --git a/lib/Doctrine/Migrations/Configuration/Exception/UnableToLoadResource.php b/lib/Doctrine/Migrations/Configuration/Exception/UnableToLoadResource.php deleted file mode 100644 index af36504e2d..0000000000 --- a/lib/Doctrine/Migrations/Configuration/Exception/UnableToLoadResource.php +++ /dev/null @@ -1,16 +0,0 @@ - $input - * - * @return array - */ - final protected function getDirectoryRelativeToFile(string $file, array $input) : array - { - foreach ($input as $ns => $dir) { - $path = realpath(dirname($file) . '/' . $dir); - - $input[$ns] = $path !== false ? $path : $dir; - } - - return $input; - } -} diff --git a/lib/Doctrine/Migrations/Configuration/Loader/JsonFileLoader.php b/lib/Doctrine/Migrations/Configuration/Loader/JsonFileLoader.php deleted file mode 100644 index 33946685cb..0000000000 --- a/lib/Doctrine/Migrations/Configuration/Loader/JsonFileLoader.php +++ /dev/null @@ -1,58 +0,0 @@ -arrayLoader = new ArrayLoader(); - } - - /** - * @param mixed $file - */ - public function load($file) : Configuration - { - if (! file_exists($file)) { - throw FileNotFound::new(); - } - - $contents = file_get_contents($file); - - assert($contents !== false); - - $config = json_decode($contents, true); - - if (json_last_error() !== JSON_ERROR_NONE) { - throw JsonNotValid::new(); - } - - if (isset($config['migrations_paths'])) { - $config['migrations_paths'] = $this->getDirectoryRelativeToFile( - $file, - $config['migrations_paths'] - ); - } - - return $this->arrayLoader->load($config); - } -} diff --git a/lib/Doctrine/Migrations/Configuration/Loader/Loader.php b/lib/Doctrine/Migrations/Configuration/Loader/Loader.php deleted file mode 100644 index 80e6190ce8..0000000000 --- a/lib/Doctrine/Migrations/Configuration/Loader/Loader.php +++ /dev/null @@ -1,15 +0,0 @@ -arrayLoader = new ArrayLoader(); - } - - /** - * @param mixed $file - */ - public function load($file) : Configuration - { - if (! file_exists($file)) { - throw FileNotFound::new(); - } - $config = require $file; - if ($config instanceof Configuration) { - return $config; - } - - assert(is_array($config)); - if (isset($config['migrations_paths'])) { - $config['migrations_paths'] = $this->getDirectoryRelativeToFile( - $file, - $config['migrations_paths'] - ); - } - - return $this->arrayLoader->load($config); - } -} diff --git a/lib/Doctrine/Migrations/DependencyFactory.php b/lib/Doctrine/Migrations/DependencyFactory.php index 2a8d25f4dc..35a23700a3 100644 --- a/lib/Doctrine/Migrations/DependencyFactory.php +++ b/lib/Doctrine/Migrations/DependencyFactory.php @@ -6,6 +6,8 @@ use Doctrine\DBAL\Connection; use Doctrine\Migrations\Configuration\Configuration; +use Doctrine\Migrations\Configuration\Connection\ConnectionLoader; +use Doctrine\Migrations\Configuration\EntityManager\EntityManagerLoader; use Doctrine\Migrations\Exception\FrozenDependencies; use Doctrine\Migrations\Exception\MissingDependency; use Doctrine\Migrations\Finder\GlobFinder; @@ -48,8 +50,6 @@ /** * The DependencyFactory is responsible for wiring up and managing internal class dependencies. - * - * @internal */ class DependencyFactory { @@ -73,18 +73,53 @@ class DependencyFactory /** @var bool */ private $frozen = false; - public function __construct(Configuration $configuration, Connection $connection, ?EntityManagerInterface $em = null, ?LoggerInterface $logger = null) + /** @var Configuration\ConfigurationLoader */ + private $configurationLoader; + + /** @var ConnectionLoader */ + private $connectionLoader; + + /** @var EntityManagerLoader|null */ + private $emLoader; + + public static function fromConnection( + Configuration\ConfigurationLoader $configurationLoader, + ConnectionLoader $connectionLoader, + ?LoggerInterface $logger = null + ) : self { + $dependencyFactory = new self($logger); + $dependencyFactory->configurationLoader = $configurationLoader; + $dependencyFactory->connectionLoader = $connectionLoader; + + return $dependencyFactory; + } + + public static function fromEntityManager( + Configuration\ConfigurationLoader $configurationLoader, + EntityManagerLoader $emLoader, + ?LoggerInterface $logger = null + ) : self { + $dependencyFactory = new self($logger); + $dependencyFactory->configurationLoader = $configurationLoader; + $dependencyFactory->emLoader = $emLoader; + + return $dependencyFactory; + } + + private function __construct(?LoggerInterface $logger) + { + $this->logger = $logger ?: new NullLogger(); + } + + public function isFrozen() : bool { - $this->configuration = $configuration; - $this->logger = $logger ?: new NullLogger(); - $this->connection = $connection; - $this->em = $em; + return $this->frozen; } public function freeze() : void { $this->frozen = true; - $this->configuration->freeze(); + $this->getConfiguration()->freeze(); } private function assertNotFrozen() : void @@ -94,16 +129,48 @@ private function assertNotFrozen() : void } } + public function hasEntityManager() : bool + { + return $this->emLoader !== null; + } + public function getConfiguration() : Configuration { + if ($this->configuration === null) { + $this->configuration = $this->configurationLoader->getConfiguration(); + } + return $this->configuration; } public function getConnection() : Connection { + if ($this->connection === null) { + $this->connection = $this->hasEntityManager() + ? $this->getEntityManager()->getConnection() + : $this->connectionLoader->getConnection(); + } + return $this->connection; } + public function getEntityManager() : EntityManagerInterface + { + if ($this->em === null) { + if ($this->emLoader === null) { + throw MissingDependency::noEntityManager(); + } + $this->em = $this->emLoader->getEntityManager(); + } + + return $this->em; + } + + public function getLogger() : LoggerInterface + { + return $this->logger; + } + public function getSorter() : ?callable { return $this->getDependency(self::MIGRATIONS_SORTER, static function () { @@ -133,7 +200,7 @@ public function getSchemaDumper() : SchemaDumper return $this->getDependency(SchemaDumper::class, function () : SchemaDumper { $excludedTables = []; - $metadataConfig = $this->configuration->getMetadataStorageConfiguration(); + $metadataConfig = $this->getConfiguration()->getMetadataStorageConfiguration(); if ($metadataConfig instanceof TableMetadataStorageConfiguration) { $excludedTables[] = sprintf('/^%s$/', preg_quote($metadataConfig->getTableName(), '/')); } @@ -151,11 +218,7 @@ public function getSchemaDumper() : SchemaDumper private function getSchemaProvider() : SchemaProvider { return $this->getDependency(SchemaProvider::class, function () : SchemaProvider { - if ($this->em === null) { - throw new MissingDependency('The doctrine entity manager should be provided in order to be able to instantiate SchemaProvider'); - } - - return new OrmSchemaProvider($this->em); + return new OrmSchemaProvider($this->getEntityManager()); }); } @@ -178,8 +241,8 @@ public function getSchemaDiffProvider() : SchemaDiffProvider return $this->getDependency(SchemaDiffProvider::class, function () : LazySchemaDiffProvider { return LazySchemaDiffProvider::fromDefaultProxyFactoryConfiguration( new DBALSchemaDiffProvider( - $this->connection->getSchemaManager(), - $this->connection->getDatabasePlatform() + $this->getConnection()->getSchemaManager(), + $this->getConnection()->getDatabasePlatform() ) ); }); @@ -195,7 +258,7 @@ public function getFileBuilder() : FileBuilder public function getParameterFormatter() : ParameterFormatter { return $this->getDependency(ParameterFormatter::class, function () : ParameterFormatter { - return new InlineParameterFormatter($this->connection); + return new InlineParameterFormatter($this->getConnection()); }); } @@ -242,29 +305,19 @@ public function getMetadataStorage() : MetadataStorage { return $this->getDependency(MetadataStorage::class, function () : MetadataStorage { return new TableMetadataStorage( - $this->connection, + $this->getConnection(), $this->getMetadataStorageConfiguration() ); }); } - public function getEntityManager() : ?EntityManagerInterface - { - return $this->em; - } - - public function getLogger() : LoggerInterface - { - return $this->logger; - } - public function getVersionExecutor() : Executor { return $this->getDependency(Executor::class, function () : Executor { return new DbalExecutor( $this->getMetadataStorage(), $this->getEventDispatcher(), - $this->connection, + $this->getConnection(), $this->getSchemaDiffProvider(), $this->getLogger(), $this->getParameterFormatter(), @@ -326,7 +379,7 @@ public function getMigrationSqlGenerator() : SqlGenerator return $this->getDependency(SqlGenerator::class, function () : SqlGenerator { return new SqlGenerator( $this->getConfiguration(), - $this->connection->getDatabasePlatform() + $this->getConnection()->getDatabasePlatform() ); }); } @@ -345,7 +398,7 @@ public function getMigrationStatusInfosHelper() : MigrationStatusInfosHelper return $this->getDependency(MigrationStatusInfosHelper::class, function () : MigrationStatusInfosHelper { return new MigrationStatusInfosHelper( $this->getConfiguration(), - $this->connection, + $this->getConnection(), $this->getVersionAliasResolver() ); }); @@ -355,7 +408,7 @@ public function getMigrator() : Migrator { return $this->getDependency(Migrator::class, function () : Migrator { return new DbalMigrator( - $this->connection, + $this->getConnection(), $this->getEventDispatcher(), $this->getVersionExecutor(), $this->logger, diff --git a/lib/Doctrine/Migrations/Exception/DependencyException.php b/lib/Doctrine/Migrations/Exception/DependencyException.php new file mode 100644 index 0000000000..61f73d1d44 --- /dev/null +++ b/lib/Doctrine/Migrations/Exception/DependencyException.php @@ -0,0 +1,9 @@ +dependencyFactory = $dependencyFactory; @@ -39,18 +37,22 @@ public function __construct(?string $name = null, ?DependencyFactory $dependency protected function configure() : void { + if ($this->dependencyFactory !== null) { + return; + } $this->addOption( 'configuration', null, - InputOption::VALUE_OPTIONAL, - 'The path to a migrations configuration file.' + InputOption::VALUE_REQUIRED, + 'The path to a migrations configuration file. [default: any of migrations.{php,xml,json,yml,yaml}]' ); $this->addOption( 'db-configuration', null, - InputOption::VALUE_OPTIONAL, - 'The path to a database connection configuration file.' + InputOption::VALUE_REQUIRED, + 'The path to a database connection configuration file.', + 'migrations-db.php' ); } @@ -68,35 +70,22 @@ protected function outputHeader( protected function initialize(InputInterface $input, OutputInterface $output) : void { - if ($this->dependencyFactory !== null) { - $this->dependencyFactory->freeze(); - - return; - } - - $helperSet = $this->getHelperSet() ?: new HelperSet(); - - if ($helperSet->has('configuration') && $helperSet->get('configuration') instanceof ConfigurationHelper) { - /** @var MigrationsConfigurationHelper $configHelper */ - $configHelper = $helperSet->get('configuration'); - } else { - $configHelper = new MigrationsConfigurationHelper(); + if ($this->dependencyFactory === null) { + $configurationLoader = new ConfigurationFileWithFallback( + is_string($input->getOption('configuration')) + ? $input->getOption('configuration') + : null + ); + $connectionLoader = new ConfigurationFile((string) $input->getOption('db-configuration')); + $this->dependencyFactory = DependencyFactory::fromConnection($configurationLoader, $connectionLoader); } - $configuration = $configHelper->getConfiguration($input); - - $dbConfig = is_string($input->getOption('db-configuration')) ? $input->getOption('db-configuration'): null; - - $connection = (new ConnectionLoader()) - ->getConnection($dbConfig, $helperSet); - - $em = null; - if ($helperSet->has('em') && $helperSet->get('em') instanceof EntityManagerHelper) { - $em = $helperSet->get('em')->getEntityManager(); + if ($this->dependencyFactory->isFrozen()) { + return; } - $logger = new ConsoleLogger($output); - $this->dependencyFactory = new DependencyFactory($configuration, $connection, $em, $logger); + $logger = new ConsoleLogger($output); + $this->dependencyFactory->setService(LoggerInterface::class, $logger); $this->dependencyFactory->freeze(); } diff --git a/lib/Doctrine/Migrations/Tools/Console/ConnectionLoader.php b/lib/Doctrine/Migrations/Tools/Console/ConnectionLoader.php deleted file mode 100644 index b2652aed61..0000000000 --- a/lib/Doctrine/Migrations/Tools/Console/ConnectionLoader.php +++ /dev/null @@ -1,34 +0,0 @@ -getConnection(); - } -} diff --git a/lib/Doctrine/Migrations/Tools/Console/ConsoleRunner.php b/lib/Doctrine/Migrations/Tools/Console/ConsoleRunner.php index bf8921d47a..6809a4da50 100644 --- a/lib/Doctrine/Migrations/Tools/Console/ConsoleRunner.php +++ b/lib/Doctrine/Migrations/Tools/Console/ConsoleRunner.php @@ -4,6 +4,7 @@ namespace Doctrine\Migrations\Tools\Console; +use Doctrine\Migrations\DependencyFactory; use Doctrine\Migrations\Tools\Console\Command\DiffCommand; use Doctrine\Migrations\Tools\Console\Command\DoctrineCommand; use Doctrine\Migrations\Tools\Console\Command\DumpSchemaCommand; @@ -17,8 +18,13 @@ use Doctrine\Migrations\Tools\Console\Command\UpToDateCommand; use Doctrine\Migrations\Tools\Console\Command\VersionCommand; use PackageVersions\Versions; +use RuntimeException; use Symfony\Component\Console\Application; -use Symfony\Component\Console\Helper\HelperSet; +use const DIRECTORY_SEPARATOR; +use function file_exists; +use function getcwd; +use function is_readable; +use function sprintf; /** * The ConsoleRunner class is used to create the Symfony Console application for the Doctrine Migrations console. @@ -29,44 +35,86 @@ */ class ConsoleRunner { + public static function findDependencyFactory() : ?DependencyFactory + { + // Support for using the Doctrine ORM convention of providing a `cli-config.php` file. + $configurationDirectories = [ + getcwd(), + getcwd() . DIRECTORY_SEPARATOR . 'config', + ]; + + $configurationFile = null; + foreach ($configurationDirectories as $configurationDirectory) { + $configurationFilePath = $configurationDirectory . DIRECTORY_SEPARATOR . 'cli-config.php'; + + if (! file_exists($configurationFilePath)) { + continue; + } + + $configurationFile = $configurationFilePath; + break; + } + + $dependencyFactory = null; + if ($configurationFile !== null) { + if (! is_readable($configurationFile)) { + throw new RuntimeException(sprintf( + 'Configuration file "%s" cannot be read.', + $configurationFile + )); + } + + $dependencyFactory = require $configurationFile; + } + + if ($dependencyFactory !== null && ! ($dependencyFactory instanceof DependencyFactory)) { + throw new RuntimeException(sprintf( + 'Configuration file "%s" must return an instance of "%s"', + $configurationFile, + DependencyFactory::class + )); + } + + return $dependencyFactory; + } + /** @param DoctrineCommand[] $commands */ - public static function run(HelperSet $helperSet, array $commands = []) : void + public static function run(array $commands = [], ?DependencyFactory $dependencyFactory = null) : void { - $cli = static::createApplication($helperSet, $commands); + $cli = static::createApplication($commands, $dependencyFactory); $cli->run(); } /** @param DoctrineCommand[] $commands */ - public static function createApplication(HelperSet $helperSet, array $commands = []) : Application + public static function createApplication(array $commands = [], ?DependencyFactory $dependencyFactory = null) : Application { $cli = new Application('Doctrine Migrations', Versions::getVersion('doctrine/migrations')); $cli->setCatchExceptions(true); - $cli->setHelperSet($helperSet); - self::addCommands($cli); + self::addCommands($cli, $dependencyFactory); $cli->addCommands($commands); return $cli; } - public static function addCommands(Application $cli) : void + public static function addCommands(Application $cli, ?DependencyFactory $dependencyFactory = null) : void { $cli->addCommands([ - new DumpSchemaCommand(), - new ExecuteCommand(), - new GenerateCommand(), - new LatestCommand(), - new MigrateCommand(), - new RollupCommand(), - new StatusCommand(), - new VersionCommand(), - new UpToDateCommand(), - new SyncMetadataCommand(), + new DumpSchemaCommand($dependencyFactory), + new ExecuteCommand($dependencyFactory), + new GenerateCommand($dependencyFactory), + new LatestCommand($dependencyFactory), + new MigrateCommand($dependencyFactory), + new RollupCommand($dependencyFactory), + new StatusCommand($dependencyFactory), + new VersionCommand($dependencyFactory), + new UpToDateCommand($dependencyFactory), + new SyncMetadataCommand($dependencyFactory), ]); - if (! $cli->getHelperSet()->has('em')) { + if ($dependencyFactory === null || ! $dependencyFactory->hasEntityManager()) { return; } - $cli->add(new DiffCommand()); + $cli->add(new DiffCommand($dependencyFactory)); } } diff --git a/lib/Doctrine/Migrations/Tools/Console/Helper/MigrationsConfigurationHelper.php b/lib/Doctrine/Migrations/Tools/Console/Helper/MigrationsConfigurationHelper.php deleted file mode 100644 index 0c317a8503..0000000000 --- a/lib/Doctrine/Migrations/Tools/Console/Helper/MigrationsConfigurationHelper.php +++ /dev/null @@ -1,90 +0,0 @@ -loader = $loader ?: new ConfigurationLoader(); - } - - public function getConfiguration(InputInterface $input) : Configuration - { - /** - * If a configuration option is passed to the command line, use that configuration - * instead of any other one. - */ - $configurationFile = $input->getOption('configuration'); - - if ($configurationFile !== null && is_string($configurationFile)) { - return $this->loadConfig($configurationFile); - } - - /** - * If no any other config has been found, look for default config file in the path. - */ - $defaultConfig = [ - 'migrations.xml', - 'migrations.yml', - 'migrations.yaml', - 'migrations.json', - 'migrations.php', - ]; - - foreach ($defaultConfig as $config) { - if ($this->configExists($config)) { - return $this->loadConfig($config); - } - } - - return $this->loader->getLoader('array')->load([]); - } - - private function configExists(string $config) : bool - { - return file_exists($config); - } - - /** - * @throws FileTypeNotSupported - */ - private function loadConfig(string $configFile) : Configuration - { - $extension = pathinfo($configFile, PATHINFO_EXTENSION); - - try { - return $this->loader->getLoader($extension)->load($configFile); - } catch (UnknownLoader $e) { - throw FileTypeNotSupported::new(); - } - } - - /** - * {@inheritdoc} - */ - public function getName() : string - { - return 'configuration'; - } -} diff --git a/phpstan.neon.dist b/phpstan.neon.dist index 40660c1334..066e88f29b 100644 --- a/phpstan.neon.dist +++ b/phpstan.neon.dist @@ -14,7 +14,7 @@ parameters: - '~Variable method call on Doctrine\\Migrations\\AbstractMigration~' - message: '~^Variable property access on mixed\.$~' - path: %currentWorkingDirectory%/lib/Doctrine/Migrations/Configuration/Loader/XmlFileLoader.php + path: %currentWorkingDirectory%/lib/Doctrine/Migrations/Configuration/Configuration/XmlFile.php - message: '~^Call to function is_bool\(\) with bool will always evaluate to true\.$~' path: %currentWorkingDirectory%/lib/Doctrine/Migrations/InlineParameterFormatter.php diff --git a/tests/Doctrine/Migrations/Tests/Configuration/Configuration/ArrayLoaderTest.php b/tests/Doctrine/Migrations/Tests/Configuration/Configuration/ArrayLoaderTest.php new file mode 100644 index 0000000000..e8471a045c --- /dev/null +++ b/tests/Doctrine/Migrations/Tests/Configuration/Configuration/ArrayLoaderTest.php @@ -0,0 +1,20 @@ +expectException(InvalidConfigurationKey::class); + $this->expectExceptionMessage('Migrations configuration key "foo" does not exist'); + $loader = new ConfigurationArray(['foo' => 'aaa']); + $loader->getConfiguration(); + } +} diff --git a/tests/Doctrine/Migrations/Tests/Configuration/Configuration/ConfigurationFileWithFallbackTest.php b/tests/Doctrine/Migrations/Tests/Configuration/Configuration/ConfigurationFileWithFallbackTest.php new file mode 100644 index 0000000000..09971c40c2 --- /dev/null +++ b/tests/Doctrine/Migrations/Tests/Configuration/Configuration/ConfigurationFileWithFallbackTest.php @@ -0,0 +1,51 @@ +getConfiguration(); + + self::assertSame('Doctrine Sandbox Migrations', $configuration->getName()); + } finally { + chdir($dir); + } + } + + public function testFileLoaderFallback() : void + { + $dir = getcwd() ?: '.'; + chdir(__DIR__ . '/../_files_loader'); + + try { + $loader = new ConfigurationFileWithFallback(); + $configuration = $loader->getConfiguration(); + + self::assertSame('Doctrine Sandbox Migrations FilesLoader', $configuration->getName()); + } finally { + chdir($dir); + } + } + + public function testMissingConfig() : void + { + $this->expectException(MissingConfigurationFile::class); + $loader = new ConfigurationFileWithFallback(); + $configuration = $loader->getConfiguration(); + } +} diff --git a/tests/Doctrine/Migrations/Tests/Configuration/Configuration/FormattedFileTest.php b/tests/Doctrine/Migrations/Tests/Configuration/Configuration/FormattedFileTest.php new file mode 100644 index 0000000000..138e7e8fc8 --- /dev/null +++ b/tests/Doctrine/Migrations/Tests/Configuration/Configuration/FormattedFileTest.php @@ -0,0 +1,20 @@ +expectException(InvalidConfigurationFormat::class); + + $loader = new FormattedFile('migrations.abc'); + $loader->getConfiguration(); + } +} diff --git a/tests/Doctrine/Migrations/Tests/Configuration/Configuration/JsonLoaderTest.php b/tests/Doctrine/Migrations/Tests/Configuration/Configuration/JsonLoaderTest.php new file mode 100644 index 0000000000..91b1e0489d --- /dev/null +++ b/tests/Doctrine/Migrations/Tests/Configuration/Configuration/JsonLoaderTest.php @@ -0,0 +1,24 @@ +getConfiguration(); + } + + public function testMalformed() : void + { + $this->expectException(Configuration\Exception\JsonNotValid::class); + $this->load('malformed'); + } +} diff --git a/tests/Doctrine/Migrations/Tests/Configuration/Loader/AbstractLoaderTest.php b/tests/Doctrine/Migrations/Tests/Configuration/Configuration/LoaderTest.php similarity index 95% rename from tests/Doctrine/Migrations/Tests/Configuration/Loader/AbstractLoaderTest.php rename to tests/Doctrine/Migrations/Tests/Configuration/Configuration/LoaderTest.php index 65ce44184b..e9bf96b91d 100644 --- a/tests/Doctrine/Migrations/Tests/Configuration/Loader/AbstractLoaderTest.php +++ b/tests/Doctrine/Migrations/Tests/Configuration/Configuration/LoaderTest.php @@ -2,10 +2,10 @@ declare(strict_types=1); -namespace Doctrine\Migrations\Tests\Configuration\Loader; +namespace Doctrine\Migrations\Tests\Configuration\Configuration; use Doctrine\Migrations\Configuration\Configuration; -use Doctrine\Migrations\Configuration\Exception\InvalidConfigurationKey; +use Doctrine\Migrations\Configuration\Configuration\Exception\InvalidConfigurationKey; use Doctrine\Migrations\Exception\MigrationException; use Doctrine\Migrations\Metadata\Storage\TableMetadataStorageConfiguration; use InvalidArgumentException; @@ -13,7 +13,7 @@ use const DIRECTORY_SEPARATOR; use function dirname; -abstract class AbstractLoaderTest extends TestCase +abstract class LoaderTest extends TestCase { abstract public function load(string $prefix = '') : Configuration; diff --git a/tests/Doctrine/Migrations/Tests/Configuration/Loader/PhpLoaderTest.php b/tests/Doctrine/Migrations/Tests/Configuration/Configuration/PhpLoaderTest.php similarity index 50% rename from tests/Doctrine/Migrations/Tests/Configuration/Loader/PhpLoaderTest.php rename to tests/Doctrine/Migrations/Tests/Configuration/Configuration/PhpLoaderTest.php index f76cc622c8..9a00286dac 100644 --- a/tests/Doctrine/Migrations/Tests/Configuration/Loader/PhpLoaderTest.php +++ b/tests/Doctrine/Migrations/Tests/Configuration/Configuration/PhpLoaderTest.php @@ -2,18 +2,18 @@ declare(strict_types=1); -namespace Doctrine\Migrations\Tests\Configuration\Loader; +namespace Doctrine\Migrations\Tests\Configuration\Configuration; use Doctrine\Migrations\Configuration\Configuration; -use Doctrine\Migrations\Configuration\Loader\PhpFileLoader; +use Doctrine\Migrations\Configuration\Configuration\PhpFile; -class PhpLoaderTest extends AbstractLoaderTest +class PhpLoaderTest extends LoaderTest { public function load(string $prefix = '') : Configuration { - $loader = new PhpFileLoader(); + $loader = new PhpFile(__DIR__ . '/../_files/config' . ($prefix!==''? ('_' . $prefix) : '') . '.php'); - return $loader->load(__DIR__ . '/../_files/config' . ($prefix!==''? ('_' . $prefix) : '') . '.php'); + return $loader->getConfiguration(); } public function testLoadInline() : void diff --git a/tests/Doctrine/Migrations/Tests/Configuration/Configuration/XmlLoaderTest.php b/tests/Doctrine/Migrations/Tests/Configuration/Configuration/XmlLoaderTest.php new file mode 100644 index 0000000000..e0dfbd1b90 --- /dev/null +++ b/tests/Doctrine/Migrations/Tests/Configuration/Configuration/XmlLoaderTest.php @@ -0,0 +1,32 @@ +getConfiguration(); + } + + public function testConfigurationWithInvalidOption() : void + { + $this->expectException(Configuration\Exception\XmlNotValid::class); + + $this->load('invalid'); + } + + public function testMalformed() : void + { + $this->expectException(Configuration\Exception\XmlNotValid::class); + + $this->load('malformed'); + } +} diff --git a/tests/Doctrine/Migrations/Tests/Configuration/Configuration/YamlLoaderTest.php b/tests/Doctrine/Migrations/Tests/Configuration/Configuration/YamlLoaderTest.php new file mode 100644 index 0000000000..6ba6f8746b --- /dev/null +++ b/tests/Doctrine/Migrations/Tests/Configuration/Configuration/YamlLoaderTest.php @@ -0,0 +1,25 @@ +getConfiguration(); + } + + public function testMalformed() : void + { + $this->expectException(Configuration\Exception\YamlNotValid::class); + + $this->load('malformed'); + } +} diff --git a/tests/Doctrine/Migrations/Tests/Configuration/ConfigurationLoaderTest.php b/tests/Doctrine/Migrations/Tests/Configuration/ConfigurationLoaderTest.php deleted file mode 100644 index 05b21af59a..0000000000 --- a/tests/Doctrine/Migrations/Tests/Configuration/ConfigurationLoaderTest.php +++ /dev/null @@ -1,57 +0,0 @@ -loader = new ConfigurationLoader(); - } - - public function testAdd() : void - { - $loader = $this->createMock(Loader::class); - $this->loader->addLoader('foo', $loader); - - self::assertSame($loader, $this->loader->getLoader('foo')); - } - - public function testUnknownLoader() : void - { - $this->expectException(UnknownLoader::class); - $this->expectExceptionMessage('Unknown configuration loader "foo".'); - $this->loader->getLoader('foo'); - } - - public function testDefaults() : void - { - $defaults = [ - 'array' => ArrayLoader::class, - 'xml' => XmlFileLoader::class, - 'yaml' => YamlFileLoader::class, - 'yml' => YamlFileLoader::class, - 'php' => PhpFileLoader::class, - 'json' => JsonFileLoader::class, - ]; - - foreach ($defaults as $name => $class) { - self::assertInstanceOf($class, $this->loader->getLoader($name)); - } - } -} diff --git a/tests/Doctrine/Migrations/Tests/Configuration/Connection/ConnectionLoaderTest.php b/tests/Doctrine/Migrations/Tests/Configuration/Connection/ConnectionLoaderTest.php new file mode 100644 index 0000000000..396d607e54 --- /dev/null +++ b/tests/Doctrine/Migrations/Tests/Configuration/Connection/ConnectionLoaderTest.php @@ -0,0 +1,54 @@ +createMock(Connection::class); + $loader = new ExistingConnection($conn); + + self::assertSame($conn, $loader->getConnection()); + } + + public function testArrayConnectionConfigurationLoader() : void + { + $loader = new ConfigurationFile(__DIR__ . '/_files/sqlite-connection.php'); + $conn = $loader->getConnection(); + + self::assertInstanceOf(SqlitePlatform::class, $conn->getDatabasePlatform()); + } + + public function testArrayConnectionConfigurationLoaderWithConnectionInstance() : void + { + $loader = new ConfigurationFile(__DIR__ . '/_files/sqlite-connection-instance.php'); + $conn = $loader->getConnection(); + + self::assertInstanceOf(SqlitePlatform::class, $conn->getDatabasePlatform()); + } + + public function testArrayConnectionConfigurationLoaderInvalid() : void + { + $this->expectException(InvalidConfiguration::class); + $loader = new ConfigurationFile(__DIR__ . '/_files/sqlite-connection-invalid.php'); + $loader->getConnection(); + } + + public function testArrayConnectionConfigurationLoaderNotFound() : void + { + $this->expectException(FileNotFound::class); + $loader = new ConfigurationFile(__DIR__ . '/_files/not-found.php'); + $loader->getConnection(); + } +} diff --git a/tests/Doctrine/Migrations/Tests/Configuration/Connection/Loader/ConnectionLoaderTest.php b/tests/Doctrine/Migrations/Tests/Configuration/Connection/Loader/ConnectionLoaderTest.php deleted file mode 100644 index 18060a60b6..0000000000 --- a/tests/Doctrine/Migrations/Tests/Configuration/Connection/Loader/ConnectionLoaderTest.php +++ /dev/null @@ -1,78 +0,0 @@ -expectException(ConnectionNotSpecified::class); - $loader = new NoConnectionLoader(); - $loader->getConnection(); - } - - public function testArrayConnectionConfigurationLoader() : void - { - $loader = new ArrayConnectionConfigurationLoader(__DIR__ . '/sqlite-connection.php', new NoConnectionLoader()); - $conn = $loader->getConnection(); - - self::assertInstanceOf(SqlitePlatform::class, $conn->getDatabasePlatform()); - } - - public function testArrayConnectionConfigurationLoaderInvalid() : void - { - $this->expectException(InvalidConfiguration::class); - $loader = new ArrayConnectionConfigurationLoader(__DIR__ . '/sqlite-connection-invalid.php', new NoConnectionLoader()); - $loader->getConnection(); - } - - public function testArrayConnectionConfigurationLoaderNotFound() : void - { - $this->expectException(ConnectionNotSpecified::class); - $loader = new ArrayConnectionConfigurationLoader(__DIR__ . '/not-found.php', new NoConnectionLoader()); - $loader->getConnection(); - } - - public function testArrayConnectionConfigurationLoaderNoFile() : void - { - $this->expectException(ConnectionNotSpecified::class); - $loader = new ArrayConnectionConfigurationLoader(null, new NoConnectionLoader()); - $loader->getConnection(); - } - - public function testConnectionHelperLoader() : void - { - $connection = $this->createMock(Connection::class); - - $helper = $this->createMock(ConnectionHelper::class); - $helper->expects(self::once())->method('getConnection')->willReturn($connection); - - $helperSet = new HelperSet(); - $helperSet->set($helper, 'connection'); - $loader = new ConnectionHelperLoader('connection', new NoConnectionLoader(), $helperSet); - $conn = $loader->getConnection(); - - self::assertSame($connection, $conn); - } - - public function testConnectionHelperLoaderNoHelper() : void - { - $this->expectException(ConnectionNotSpecified::class); - $helperSet = new HelperSet(); - $loader = new ConnectionHelperLoader('connection', new NoConnectionLoader(), $helperSet); - $loader->getConnection(); - } -} diff --git a/tests/Doctrine/Migrations/Tests/Tools/Console/_files/migrations-db.php b/tests/Doctrine/Migrations/Tests/Configuration/Connection/_files/migrations-db.php similarity index 100% rename from tests/Doctrine/Migrations/Tests/Tools/Console/_files/migrations-db.php rename to tests/Doctrine/Migrations/Tests/Configuration/Connection/_files/migrations-db.php diff --git a/tests/Doctrine/Migrations/Tests/Configuration/Connection/_files/sqlite-connection-instance.php b/tests/Doctrine/Migrations/Tests/Configuration/Connection/_files/sqlite-connection-instance.php new file mode 100644 index 0000000000..fb136ac993 --- /dev/null +++ b/tests/Doctrine/Migrations/Tests/Configuration/Connection/_files/sqlite-connection-instance.php @@ -0,0 +1,7 @@ + 'pdo_sqlite', 'memory' => true]); diff --git a/tests/Doctrine/Migrations/Tests/Configuration/Connection/Loader/sqlite-connection-invalid.php b/tests/Doctrine/Migrations/Tests/Configuration/Connection/_files/sqlite-connection-invalid.php similarity index 100% rename from tests/Doctrine/Migrations/Tests/Configuration/Connection/Loader/sqlite-connection-invalid.php rename to tests/Doctrine/Migrations/Tests/Configuration/Connection/_files/sqlite-connection-invalid.php diff --git a/tests/Doctrine/Migrations/Tests/Configuration/Connection/Loader/sqlite-connection.php b/tests/Doctrine/Migrations/Tests/Configuration/Connection/_files/sqlite-connection.php similarity index 100% rename from tests/Doctrine/Migrations/Tests/Configuration/Connection/Loader/sqlite-connection.php rename to tests/Doctrine/Migrations/Tests/Configuration/Connection/_files/sqlite-connection.php diff --git a/tests/Doctrine/Migrations/Tests/Configuration/EntityManager/EntityManagerTest.php b/tests/Doctrine/Migrations/Tests/Configuration/EntityManager/EntityManagerTest.php new file mode 100644 index 0000000000..f47e8669a1 --- /dev/null +++ b/tests/Doctrine/Migrations/Tests/Configuration/EntityManager/EntityManagerTest.php @@ -0,0 +1,56 @@ +createMock(EntityManager::class); + $loader = new ExistingEntityManager($em); + + self::assertSame($em, $loader->getEntityManager()); + } + + public function testArrayEntityManagerConfigurationLoader() : void + { + $loader = new ConfigurationFile(__DIR__ . '/_files/em-loader.php'); + $em = $loader->getEntityManager(); + + self::assertSame('Foo', $em->getConfiguration()->getProxyNamespace()); + self::assertInstanceOf(SqlitePlatform::class, $em->getConnection()->getDatabasePlatform()); + } + + public function testArrayEntityManagerConfigurationLoaderWithEntityManagerInstance() : void + { + $loader = new ConfigurationFile(__DIR__ . '/_files/migrations-em.php'); + $em = $loader->getEntityManager(); + + self::assertSame('Foo', $em->getConfiguration()->getProxyNamespace()); + self::assertInstanceOf(SqlitePlatform::class, $em->getConnection()->getDatabasePlatform()); + } + + public function testArrayEntityManagerConfigurationLoaderInvalid() : void + { + $this->expectException(InvalidConfiguration::class); + $loader = new ConfigurationFile(__DIR__ . '/_files/em-invalid.php'); + $loader->getEntityManager(); + } + + public function testArrayEntityManagerConfigurationLoaderNotFound() : void + { + $this->expectException(FileNotFound::class); + $loader = new ConfigurationFile(__DIR__ . '/_files/not-found.php'); + $loader->getEntityManager(); + } +} diff --git a/tests/Doctrine/Migrations/Tests/Configuration/EntityManager/_files/em-invalid.php b/tests/Doctrine/Migrations/Tests/Configuration/EntityManager/_files/em-invalid.php new file mode 100644 index 0000000000..174d7fd709 --- /dev/null +++ b/tests/Doctrine/Migrations/Tests/Configuration/EntityManager/_files/em-invalid.php @@ -0,0 +1,3 @@ + 'pdo_sqlite', 'memory' => true]); + + $conf = new Configuration(); + $conf->setProxyDir(__DIR__); + $conf->setProxyNamespace('Foo'); + $conf->setMetadataDriverImpl(new PHPDriver('')); + + return EntityManager::create($conn, $conf); + } +}; diff --git a/tests/Doctrine/Migrations/Tests/Configuration/EntityManager/_files/migrations-em.php b/tests/Doctrine/Migrations/Tests/Configuration/EntityManager/_files/migrations-em.php new file mode 100644 index 0000000000..8dbbf52b5e --- /dev/null +++ b/tests/Doctrine/Migrations/Tests/Configuration/EntityManager/_files/migrations-em.php @@ -0,0 +1,17 @@ + 'pdo_sqlite', 'memory' => true]); + +$conf = new Configuration(); +$conf->setProxyDir(__DIR__); +$conf->setProxyNamespace('Foo'); +$conf->setMetadataDriverImpl(new PHPDriver('')); + +return EntityManager::create($conn, $conf); diff --git a/tests/Doctrine/Migrations/Tests/Configuration/Loader/ArrayLoaderTest.php b/tests/Doctrine/Migrations/Tests/Configuration/Loader/ArrayLoaderTest.php deleted file mode 100644 index 047c2fca02..0000000000 --- a/tests/Doctrine/Migrations/Tests/Configuration/Loader/ArrayLoaderTest.php +++ /dev/null @@ -1,37 +0,0 @@ -expectException(UnableToLoadResource::class); - $this->expectExceptionMessage('The provided resource can not be loaded by the loader "Doctrine\Migrations\Configuration\Loader\ArrayLoader".'); - $loader = new ArrayLoader(); - $loader->load(null); - } - - public function testInvalidKey() : void - { - $this->expectException(InvalidConfigurationKey::class); - $this->expectExceptionMessage('Migrations configuration key "foo" does not exist'); - $loader = new ArrayLoader(); - $loader->load(['foo' => 'aaa']); - } - - public function testInvalidKeyInteger() : void - { - $this->expectException(InvalidConfigurationKey::class); - $this->expectExceptionMessage('Migrations configuration key "0" does not exist.'); - $loader = new ArrayLoader(); - $loader->load(['aaa']); - } -} diff --git a/tests/Doctrine/Migrations/Tests/Configuration/Loader/JsonLoaderTest.php b/tests/Doctrine/Migrations/Tests/Configuration/Loader/JsonLoaderTest.php deleted file mode 100644 index 323fe49ef0..0000000000 --- a/tests/Doctrine/Migrations/Tests/Configuration/Loader/JsonLoaderTest.php +++ /dev/null @@ -1,25 +0,0 @@ -load(__DIR__ . '/../_files/config' . ($prefix!==''? ('_' . $prefix) : '') . '.json'); - } - - public function testMalformed() : void - { - $this->expectException(JsonNotValid::class); - $this->load('malformed'); - } -} diff --git a/tests/Doctrine/Migrations/Tests/Configuration/Loader/XmlLoaderTest.php b/tests/Doctrine/Migrations/Tests/Configuration/Loader/XmlLoaderTest.php deleted file mode 100644 index 4be6592830..0000000000 --- a/tests/Doctrine/Migrations/Tests/Configuration/Loader/XmlLoaderTest.php +++ /dev/null @@ -1,33 +0,0 @@ -load(__DIR__ . '/../_files/config' . ($prefix!==''? ('_' . $prefix) : '') . '.xml'); - } - - public function testConfigurationWithInvalidOption() : void - { - $this->expectException(XmlNotValid::class); - - $this->load('invalid'); - } - - public function testMalformed() : void - { - $this->expectException(XmlNotValid::class); - - $this->load('malformed'); - } -} diff --git a/tests/Doctrine/Migrations/Tests/Configuration/Loader/YamlLoaderTest.php b/tests/Doctrine/Migrations/Tests/Configuration/Loader/YamlLoaderTest.php deleted file mode 100644 index 4c8548a100..0000000000 --- a/tests/Doctrine/Migrations/Tests/Configuration/Loader/YamlLoaderTest.php +++ /dev/null @@ -1,26 +0,0 @@ -load(__DIR__ . '/../_files/config' . ($prefix!==''? ('_' . $prefix) : '') . '.yml'); - } - - public function testMalformed() : void - { - $this->expectException(YamlNotValid::class); - - $this->load('malformed'); - } -} diff --git a/tests/Doctrine/Migrations/Tests/Configuration/_files_loader/migrations.php b/tests/Doctrine/Migrations/Tests/Configuration/_files_loader/migrations.php new file mode 100644 index 0000000000..ddaca274b4 --- /dev/null +++ b/tests/Doctrine/Migrations/Tests/Configuration/_files_loader/migrations.php @@ -0,0 +1,9 @@ + 'Doctrine Sandbox Migrations FilesLoader', + 'migrations_paths' => ['DoctrineMigrationsTest' => '.'], + +]; diff --git a/tests/Doctrine/Migrations/Tests/DependencyFactoryTest.php b/tests/Doctrine/Migrations/Tests/DependencyFactoryTest.php index 27b6665093..e7c8f38c34 100644 --- a/tests/Doctrine/Migrations/Tests/DependencyFactoryTest.php +++ b/tests/Doctrine/Migrations/Tests/DependencyFactoryTest.php @@ -6,10 +6,14 @@ use Doctrine\DBAL\Connection; use Doctrine\Migrations\Configuration\Configuration; +use Doctrine\Migrations\Configuration\Connection\ExistingConnection; +use Doctrine\Migrations\Configuration\EntityManager\ExistingEntityManager; use Doctrine\Migrations\DependencyFactory; use Doctrine\Migrations\Exception\FrozenDependencies; +use Doctrine\Migrations\Exception\MissingDependency; use Doctrine\Migrations\Finder\GlobFinder; use Doctrine\Migrations\Finder\RecursiveRegexFinder; +use Doctrine\ORM\EntityManager; use PHPUnit\Framework\MockObject\MockObject; use stdClass; @@ -18,17 +22,29 @@ final class DependencyFactoryTest extends MigrationTestCase /** @var MockObject|Connection */ private $connection; + /** @var Configuration */ + private $configuration; + + /** @var EntityManager|MockObject */ + private $entityManager; + public function setUp() : void { - $this->connection = $this->createMock(Connection::class); + $this->connection = $this->createMock(Connection::class); + $this->entityManager = $this->createMock(EntityManager::class); + $this->entityManager + ->expects(self::any()) + ->method('getConnection') + ->willReturn($this->connection); + + $this->configuration = new Configuration(); } public function testFreeze() : void { - $conf = new Configuration(); - $conf->addMigrationsDirectory('foo', 'bar'); + $this->configuration->addMigrationsDirectory('foo', 'bar'); - $di = new DependencyFactory($conf, $this->connection); + $di = DependencyFactory::fromConnection(new Configuration\ExistingConfiguration($this->configuration), new ExistingConnection($this->connection)); $di->freeze(); $this->expectException(FrozenDependencies::class); @@ -38,10 +54,9 @@ public function testFreeze() : void public function testFinderForYearMonthStructure() : void { - $conf = new Configuration(); - $conf->setMigrationsAreOrganizedByYearAndMonth(true); + $this->configuration->setMigrationsAreOrganizedByYearAndMonth(true); - $di = new DependencyFactory($conf, $this->connection); + $di = DependencyFactory::fromConnection(new Configuration\ExistingConfiguration($this->configuration), new ExistingConnection($this->connection)); $finder = $di->getMigrationsFinder(); self::assertInstanceOf(RecursiveRegexFinder::class, $finder); @@ -49,10 +64,9 @@ public function testFinderForYearMonthStructure() : void public function testFinderForYearStructure() : void { - $conf = new Configuration(); - $conf->setMigrationsAreOrganizedByYear(true); + $this->configuration->setMigrationsAreOrganizedByYear(true); - $di = new DependencyFactory($conf, $this->connection); + $di = DependencyFactory::fromConnection(new Configuration\ExistingConfiguration($this->configuration), new ExistingConnection($this->connection)); $finder = $di->getMigrationsFinder(); self::assertInstanceOf(RecursiveRegexFinder::class, $finder); @@ -60,19 +74,35 @@ public function testFinderForYearStructure() : void public function testFinder() : void { - $conf = new Configuration(); - $di = new DependencyFactory($conf, $this->connection); - $finder = $di->getMigrationsFinder(); + $this->configuration = new Configuration(); + $di = DependencyFactory::fromConnection(new Configuration\ExistingConfiguration($this->configuration), new ExistingConnection($this->connection)); + $finder = $di->getMigrationsFinder(); self::assertInstanceOf(GlobFinder::class, $finder); } public function testConnection() : void { - $conf = new Configuration(); - $di = new DependencyFactory($conf, $this->connection); - $conn = $di->getConnection(); + $di = DependencyFactory::fromConnection(new Configuration\ExistingConfiguration($this->configuration), new ExistingConnection($this->connection)); + + self::assertSame($this->connection, $di->getConnection()); + self::assertFalse($di->hasEntityManager()); + } + + public function testNoEntityManagerRaiseException() : void + { + $this->expectException(MissingDependency::class); + + $di = DependencyFactory::fromConnection(new Configuration\ExistingConfiguration($this->configuration), new ExistingConnection($this->connection)); + $di->getEntityManager(); + } + + public function testEntityManager() : void + { + $di = DependencyFactory::fromEntityManager(new Configuration\ExistingConfiguration($this->configuration), new ExistingEntityManager($this->entityManager)); - self::assertSame($this->connection, $conn); + self::assertTrue($di->hasEntityManager()); + self::assertSame($this->entityManager, $di->getEntityManager()); + self::assertSame($this->connection, $di->getConnection()); } } diff --git a/tests/Doctrine/Migrations/Tests/Tools/Console/Command/DiffCommandTest.php b/tests/Doctrine/Migrations/Tests/Tools/Console/Command/DiffCommandTest.php index 1d82aed786..739fe6fb0d 100644 --- a/tests/Doctrine/Migrations/Tests/Tools/Console/Command/DiffCommandTest.php +++ b/tests/Doctrine/Migrations/Tests/Tools/Console/Command/DiffCommandTest.php @@ -118,7 +118,7 @@ protected function setUp() : void ->willReturn($this->migrationDiffGenerator); $this->diffCommand = $this->getMockBuilder(DiffCommand::class) - ->setConstructorArgs([null, $this->dependencyFactory]) + ->setConstructorArgs([$this->dependencyFactory]) ->onlyMethods(['procOpen']) ->getMock(); } diff --git a/tests/Doctrine/Migrations/Tests/Tools/Console/Command/DoctrineCommandTest.php b/tests/Doctrine/Migrations/Tests/Tools/Console/Command/DoctrineCommandTest.php index 6dac094bbd..8c202ef573 100644 --- a/tests/Doctrine/Migrations/Tests/Tools/Console/Command/DoctrineCommandTest.php +++ b/tests/Doctrine/Migrations/Tests/Tools/Console/Command/DoctrineCommandTest.php @@ -23,7 +23,7 @@ public function testCommandFreezes() : void ->method('freeze'); $command = $this->getMockBuilder(DoctrineCommand::class) - ->setConstructorArgs(['foo', $dependencyFactory]) + ->setConstructorArgs([$dependencyFactory]) ->onlyMethods(['execute']) ->getMockForAbstractClass(); diff --git a/tests/Doctrine/Migrations/Tests/Tools/Console/Command/DumpSchemaCommandTest.php b/tests/Doctrine/Migrations/Tests/Tools/Console/Command/DumpSchemaCommandTest.php index 388c9d7a3e..5d3dfbabd5 100644 --- a/tests/Doctrine/Migrations/Tests/Tools/Console/Command/DumpSchemaCommandTest.php +++ b/tests/Doctrine/Migrations/Tests/Tools/Console/Command/DumpSchemaCommandTest.php @@ -139,6 +139,6 @@ protected function setUp() : void ->method('getMigrationRepository') ->willReturn($this->migrationRepository); - $this->dumpSchemaCommand = new DumpSchemaCommand(null, $this->dependencyFactory); + $this->dumpSchemaCommand = new DumpSchemaCommand($this->dependencyFactory); } } diff --git a/tests/Doctrine/Migrations/Tests/Tools/Console/Command/ExecuteCommandTest.php b/tests/Doctrine/Migrations/Tests/Tools/Console/Command/ExecuteCommandTest.php index 1efc641790..24998f07c2 100644 --- a/tests/Doctrine/Migrations/Tests/Tools/Console/Command/ExecuteCommandTest.php +++ b/tests/Doctrine/Migrations/Tests/Tools/Console/Command/ExecuteCommandTest.php @@ -176,7 +176,7 @@ protected function setUp() : void ->willReturn($migrationRepository); $this->executeCommand = $this->getMockBuilder(ExecuteCommand::class) - ->setConstructorArgs([null, $this->dependencyFactory]) + ->setConstructorArgs([$this->dependencyFactory]) ->onlyMethods(['canExecute']) ->getMock(); diff --git a/tests/Doctrine/Migrations/Tests/Tools/Console/Command/GenerateCommandTest.php b/tests/Doctrine/Migrations/Tests/Tools/Console/Command/GenerateCommandTest.php index f714f2dbca..3cee59e706 100644 --- a/tests/Doctrine/Migrations/Tests/Tools/Console/Command/GenerateCommandTest.php +++ b/tests/Doctrine/Migrations/Tests/Tools/Console/Command/GenerateCommandTest.php @@ -93,7 +93,7 @@ protected function setUp() : void ->willReturn($this->migrationGenerator); $this->generateCommand = $this->getMockBuilder(GenerateCommand::class) - ->setConstructorArgs([null, $this->dependencyFactory]) + ->setConstructorArgs([$this->dependencyFactory]) ->onlyMethods(['procOpen']) ->getMock(); } diff --git a/tests/Doctrine/Migrations/Tests/Tools/Console/Command/LatestCommandTest.php b/tests/Doctrine/Migrations/Tests/Tools/Console/Command/LatestCommandTest.php index bc554c236b..c3ae74710f 100644 --- a/tests/Doctrine/Migrations/Tests/Tools/Console/Command/LatestCommandTest.php +++ b/tests/Doctrine/Migrations/Tests/Tools/Console/Command/LatestCommandTest.php @@ -6,6 +6,7 @@ use Doctrine\Migrations\AbstractMigration; use Doctrine\Migrations\Configuration\Configuration; +use Doctrine\Migrations\Configuration\Connection\ExistingConnection; use Doctrine\Migrations\DependencyFactory; use Doctrine\Migrations\Metadata\Storage\MetadataStorage; use Doctrine\Migrations\Metadata\Storage\TableMetadataStorageConfiguration; @@ -42,13 +43,16 @@ protected function setUp() : void $conn = $this->getSqliteConnection(); - $dependencyFactory = new DependencyFactory($configuration, $conn); + $dependencyFactory = DependencyFactory::fromConnection( + new Configuration\ExistingConfiguration($configuration), + new ExistingConnection($conn) + ); $this->migrationRepository = $dependencyFactory->getMigrationRepository(); $this->metadataStorage = $dependencyFactory->getMetadataStorage(); $this->metadataStorage->ensureInitialized(); - $this->command = new LatestCommand(null, $dependencyFactory); + $this->command = new LatestCommand($dependencyFactory); $this->commandTester = new CommandTester($this->command); } diff --git a/tests/Doctrine/Migrations/Tests/Tools/Console/Command/MigrateCommandTest.php b/tests/Doctrine/Migrations/Tests/Tools/Console/Command/MigrateCommandTest.php index 7b1a7c22fe..932c176bfc 100644 --- a/tests/Doctrine/Migrations/Tests/Tools/Console/Command/MigrateCommandTest.php +++ b/tests/Doctrine/Migrations/Tests/Tools/Console/Command/MigrateCommandTest.php @@ -6,10 +6,12 @@ use Doctrine\Migrations\AbstractMigration; use Doctrine\Migrations\Configuration\Configuration; +use Doctrine\Migrations\Configuration\Connection\ExistingConnection; use Doctrine\Migrations\DbalMigrator; use Doctrine\Migrations\DependencyFactory; use Doctrine\Migrations\Metadata\MigrationPlanList; use Doctrine\Migrations\Metadata\Storage\MetadataStorage; +use Doctrine\Migrations\Migrator; use Doctrine\Migrations\MigratorConfiguration; use Doctrine\Migrations\QueryWriter; use Doctrine\Migrations\Tests\MigrationTestCase; @@ -24,7 +26,7 @@ class MigrateCommandTest extends MigrationTestCase { - /** @var DependencyFactory|MockObject */ + /** @var DependencyFactory */ private $dependencyFactory; /** @var Configuration */ @@ -121,10 +123,7 @@ public function testExecutedUnavailableMigrationsCancel() : void $this->storage->complete($result); $migrator = $this->createMock(DbalMigrator::class); - - $this->dependencyFactory->expects(self::any()) - ->method('getMigrator') - ->willReturn($migrator); + $this->dependencyFactory->setService(Migrator::class, $migrator); $migrator->expects(self::never()) ->method('migrate'); @@ -148,9 +147,7 @@ public function testExecuteWriteSql($arg, string $path) : void { $migrator = $this->createMock(DbalMigrator::class); - $this->dependencyFactory->expects(self::any()) - ->method('getMigrator') - ->willReturn($migrator); + $this->dependencyFactory->setService(Migrator::class, $migrator); $migrator->expects(self::once()) ->method('migrate') @@ -183,10 +180,7 @@ public function getWriteSqlValues() : array public function testExecuteMigrate() : void { $migrator = $this->createMock(DbalMigrator::class); - - $this->dependencyFactory->expects(self::any()) - ->method('getMigrator') - ->willReturn($migrator); + $this->dependencyFactory->setService(Migrator::class, $migrator); $this->migrateCommand->expects(self::once()) ->method('canExecute') @@ -209,10 +203,7 @@ public function testExecuteMigrate() : void public function testExecuteMigrateAllOrNothing() : void { $migrator = $this->createMock(DbalMigrator::class); - - $this->dependencyFactory->expects(self::any()) - ->method('getMigrator') - ->willReturn($migrator); + $this->dependencyFactory->setService(Migrator::class, $migrator); $migrator->expects(self::once()) ->method('migrate') @@ -242,9 +233,7 @@ public function testExecuteMigrateCancelExecutedUnavailableMigrations() : void $migrator = $this->createMock(DbalMigrator::class); - $this->dependencyFactory->expects(self::once()) - ->method('getMigrator') - ->willReturn($migrator); + $this->dependencyFactory->setService(Migrator::class, $migrator); $migrator->expects(self::never()) ->method('migrate'); @@ -267,10 +256,7 @@ public function testExecuteMigrateCancelExecutedUnavailableMigrations() : void public function testExecuteMigrateCancel() : void { $migrator = $this->createMock(DbalMigrator::class); - - $this->dependencyFactory->expects(self::once()) - ->method('getMigrator') - ->willReturn($migrator); + $this->dependencyFactory->setService(Migrator::class, $migrator); $migrator->expects(self::never()) ->method('migrate'); @@ -292,15 +278,10 @@ protected function setUp() : void $connection = $this->getSqliteConnection(); - $this->dependencyFactory = $this->getMockBuilder(DependencyFactory::class) - ->setConstructorArgs([$this->configuration, $connection]) - ->onlyMethods(['getMigrator', 'getQueryWriter']) - ->getMock(); + $this->dependencyFactory = DependencyFactory::fromConnection(new Configuration\ExistingConfiguration($this->configuration), new ExistingConnection($connection)); $this->queryWriter = $this->createMock(QueryWriter::class); - $this->dependencyFactory->expects(self::any()) - ->method('getQueryWriter') - ->willReturn($this->queryWriter); + $this->dependencyFactory->setService(QueryWriter::class, $this->queryWriter); $migration = $this->createMock(AbstractMigration::class); @@ -308,7 +289,7 @@ protected function setUp() : void $repo->registerMigrationInstance(new Version('A'), $migration); $this->migrateCommand = $this->getMockBuilder(MigrateCommand::class) - ->setConstructorArgs([null, $this->dependencyFactory]) + ->setConstructorArgs([$this->dependencyFactory]) ->onlyMethods(['canExecute']) ->getMock(); diff --git a/tests/Doctrine/Migrations/Tests/Tools/Console/Command/MigrationVersionTest.php b/tests/Doctrine/Migrations/Tests/Tools/Console/Command/MigrationVersionTest.php index 47a512ed4d..0fd28c14f3 100644 --- a/tests/Doctrine/Migrations/Tests/Tools/Console/Command/MigrationVersionTest.php +++ b/tests/Doctrine/Migrations/Tests/Tools/Console/Command/MigrationVersionTest.php @@ -6,6 +6,7 @@ use Doctrine\Migrations\AbstractMigration; use Doctrine\Migrations\Configuration\Configuration; +use Doctrine\Migrations\Configuration\Connection\ExistingConnection; use Doctrine\Migrations\DependencyFactory; use Doctrine\Migrations\Metadata\Storage\MetadataStorage; use Doctrine\Migrations\MigrationRepository; @@ -43,13 +44,17 @@ protected function setUp() : void $conn = $this->getSqliteConnection(); $logger = new TestLogger(); - $dependencyFactory = new DependencyFactory($configuration, $conn, null, $logger); + $dependencyFactory = DependencyFactory::fromConnection( + new Configuration\ExistingConfiguration($configuration), + new ExistingConnection($conn), + $logger + ); $this->migrationRepository = $dependencyFactory->getMigrationRepository(); $this->metadataStorage = $dependencyFactory->getMetadataStorage(); $this->metadataStorage->ensureInitialized(); - $this->command = new VersionCommand(null, $dependencyFactory); + $this->command = new VersionCommand($dependencyFactory); $this->commandTester = new CommandTester($this->command); } diff --git a/tests/Doctrine/Migrations/Tests/Tools/Console/Command/RollupCommandTest.php b/tests/Doctrine/Migrations/Tests/Tools/Console/Command/RollupCommandTest.php index c37d1c236e..cf62d6c3cd 100644 --- a/tests/Doctrine/Migrations/Tests/Tools/Console/Command/RollupCommandTest.php +++ b/tests/Doctrine/Migrations/Tests/Tools/Console/Command/RollupCommandTest.php @@ -112,6 +112,6 @@ protected function setUp() : void { $this->rollup = $this->createMock(Rollup::class); $this->dependencyFactory = $this->createMock(DependencyFactory::class); - $this->rollupCommand = new RollupCommand(null, $this->dependencyFactory); + $this->rollupCommand = new RollupCommand($this->dependencyFactory); } } diff --git a/tests/Doctrine/Migrations/Tests/Tools/Console/Command/StatusCommandTest.php b/tests/Doctrine/Migrations/Tests/Tools/Console/Command/StatusCommandTest.php index 60f053cdb5..88b2ecf0e3 100644 --- a/tests/Doctrine/Migrations/Tests/Tools/Console/Command/StatusCommandTest.php +++ b/tests/Doctrine/Migrations/Tests/Tools/Console/Command/StatusCommandTest.php @@ -7,6 +7,7 @@ use DateTimeImmutable; use Doctrine\Migrations\AbstractMigration; use Doctrine\Migrations\Configuration\Configuration; +use Doctrine\Migrations\Configuration\Connection\ExistingConnection; use Doctrine\Migrations\DependencyFactory; use Doctrine\Migrations\Metadata\Storage\MetadataStorage; use Doctrine\Migrations\Metadata\Storage\TableMetadataStorageConfiguration; @@ -47,14 +48,17 @@ protected function setUp() : void $conn = $this->getSqliteConnection(); - $dependencyFactory = new DependencyFactory($configuration, $conn); + $dependencyFactory = DependencyFactory::fromConnection( + new Configuration\ExistingConfiguration($configuration), + new ExistingConnection($conn) + ); $this->migrationRepository = $dependencyFactory->getMigrationRepository(); $this->metadataStorage = $dependencyFactory->getMetadataStorage(); $this->metadataStorage->ensureInitialized(); - $this->command = new StatusCommand(null, $dependencyFactory); + $this->command = new StatusCommand($dependencyFactory); $this->commandTester = new CommandTester($this->command); } diff --git a/tests/Doctrine/Migrations/Tests/Tools/Console/Command/SyncMetadataCommandTest.php b/tests/Doctrine/Migrations/Tests/Tools/Console/Command/SyncMetadataCommandTest.php index eac7be8e75..946343026b 100644 --- a/tests/Doctrine/Migrations/Tests/Tools/Console/Command/SyncMetadataCommandTest.php +++ b/tests/Doctrine/Migrations/Tests/Tools/Console/Command/SyncMetadataCommandTest.php @@ -48,6 +48,6 @@ protected function setUp() : void ->method('getMetadataStorage') ->willReturn($this->storage); - $this->storageCommand = new SyncMetadataCommand(null, $this->dependencyFactory); + $this->storageCommand = new SyncMetadataCommand($this->dependencyFactory); } } diff --git a/tests/Doctrine/Migrations/Tests/Tools/Console/Command/UpToDateCommandTest.php b/tests/Doctrine/Migrations/Tests/Tools/Console/Command/UpToDateCommandTest.php index ba1e6ae752..60471c0329 100644 --- a/tests/Doctrine/Migrations/Tests/Tools/Console/Command/UpToDateCommandTest.php +++ b/tests/Doctrine/Migrations/Tests/Tools/Console/Command/UpToDateCommandTest.php @@ -7,6 +7,7 @@ use Doctrine\DBAL\Connection; use Doctrine\Migrations\AbstractMigration; use Doctrine\Migrations\Configuration\Configuration; +use Doctrine\Migrations\Configuration\Connection\ExistingConnection; use Doctrine\Migrations\DependencyFactory; use Doctrine\Migrations\Exception\MigrationException; use Doctrine\Migrations\Metadata\Storage\MetadataStorage; @@ -50,13 +51,16 @@ protected function setUp() : void $this->conn = $this->getSqliteConnection(); - $dependencyFactory = new DependencyFactory($configuration, $this->conn); + $dependencyFactory = DependencyFactory::fromConnection( + new Configuration\ExistingConfiguration($configuration), + new ExistingConnection($this->conn) + ); $this->migrationRepository = $dependencyFactory->getMigrationRepository(); $this->metadataStorage = $dependencyFactory->getMetadataStorage(); $this->metadataStorage->ensureInitialized(); - $this->command = new UpToDateCommand(null, $dependencyFactory); + $this->command = new UpToDateCommand($dependencyFactory); $this->commandTester = new CommandTester($this->command); } diff --git a/tests/Doctrine/Migrations/Tests/Tools/Console/ConnectionLoaderTest.php b/tests/Doctrine/Migrations/Tests/Tools/Console/ConnectionLoaderTest.php deleted file mode 100644 index a7e30c723e..0000000000 --- a/tests/Doctrine/Migrations/Tests/Tools/Console/ConnectionLoaderTest.php +++ /dev/null @@ -1,87 +0,0 @@ -createMock(HelperSet::class); - - $dir = getcwd() ?: '.'; - chdir(__DIR__); - try { - $conn = $this->connectionLoader->getConnection('_files/sqlite-connection.php', $helperSet); - self::assertInstanceOf(SqlitePlatform::class, $conn->getDatabasePlatform()); - } finally { - chdir($dir); - } - } - - public function testGetConnectionFromArrayNotFound() : void - { - $this->expectException(ConnectionNotSpecified::class); - $helperSet = $this->createMock(HelperSet::class); - - $dir = getcwd()?: '.'; - chdir(__DIR__); - try { - $this->connectionLoader->getConnection(__DIR__ . '/_files/wrong.php', $helperSet); - } finally { - chdir($dir); - } - } - - public function testGetConnectionFromArrayFromFallbackFile() : void - { - $helperSet = $this->createMock(HelperSet::class); - - $dir = getcwd()?: '.'; - chdir(__DIR__ . '/_files'); - try { - $conn = $this->connectionLoader->getConnection(null, $helperSet); - self::assertInstanceOf(SqlitePlatform::class, $conn->getDatabasePlatform()); - } finally { - chdir($dir); - } - } - - public function testGetConnectionFromHelper() : void - { - $connection = $this->createMock(Connection::class); - - $helper = $this->createMock(ConnectionHelper::class); - $helper->expects(self::once())->method('getConnection')->willReturn($connection); - - $helperSet = new HelperSet(); - $helperSet->set($helper, 'connection'); - - $dir = getcwd()?: '.'; - chdir(__DIR__); - try { - self::assertSame($connection, $this->connectionLoader->getConnection(null, $helperSet)); - } finally { - chdir($dir); - } - } - - protected function setUp() : void - { - $this->connectionLoader = new ConnectionLoader(); - } -} diff --git a/tests/Doctrine/Migrations/Tests/Tools/Console/ConsoleRunnerTest.php b/tests/Doctrine/Migrations/Tests/Tools/Console/ConsoleRunnerTest.php index c79f4bc648..43821b3907 100644 --- a/tests/Doctrine/Migrations/Tests/Tools/Console/ConsoleRunnerTest.php +++ b/tests/Doctrine/Migrations/Tests/Tools/Console/ConsoleRunnerTest.php @@ -4,29 +4,89 @@ namespace Doctrine\Migrations\Tests\Tools\Console; +use Doctrine\Migrations\DependencyFactory; use Doctrine\Migrations\Tools\Console\ConsoleRunner; -use Doctrine\ORM\Tools\Console\Helper\EntityManagerHelper; -use PHPUnit\Framework\MockObject\MockObject; use PHPUnit\Framework\TestCase; +use RuntimeException; use Symfony\Component\Console\Application; use Symfony\Component\Console\Command\Command; use Symfony\Component\Console\Helper\HelperSet; +use function chdir; +use function getcwd; +use function realpath; +use function sprintf; /** * @covers \Doctrine\Migrations\Tools\Console\ConsoleRunner */ class ConsoleRunnerTest extends TestCase { - /** @var MockObject|EntityManagerHelper */ - private $entityManagerHelper; - /** @var Application */ private $application; - public function testRun() : void + /** + * @dataProvider getDependencyFactoryTestDirectories + */ + public function testDependencyFactory(string $directory) : void + { + $dir = getcwd() ?: '.'; + chdir($directory); + + try { + $dependencyFactory = ConsoleRunnerStub::findDependencyFactory(); + self::assertInstanceOf(DependencyFactory::class, $dependencyFactory); + self::assertSame('Doctrine Sandbox Migrations Cli', $dependencyFactory->getConfiguration()->getName()); + } finally { + chdir($dir); + } + } + + public function testInvalidCliConfigTriggersException() : void + { + $dir = getcwd() ?: '.'; + + try { + $this->expectException(RuntimeException::class); + $this->expectExceptionMessage(sprintf( + 'Configuration file "%s" must return an instance of "%s"', + realpath(__DIR__ . '/_wrong-config/cli-config.php'), + DependencyFactory::class + )); + + chdir(__DIR__ . '/_wrong-config'); + + ConsoleRunnerStub::findDependencyFactory(); + } finally { + chdir($dir); + } + } + + public function testNoDependencyFactoryWhenNoCliConfig() : void { - $helperSet = new HelperSet([]); + $dir = getcwd() ?: '.'; + chdir(__DIR__ . '/../'); + + try { + $dependencyFactory = ConsoleRunnerStub::findDependencyFactory(); + self::assertNull($dependencyFactory); + } finally { + chdir($dir); + } + } + /** + * @return array> + */ + public function getDependencyFactoryTestDirectories() : array + { + return [ + [__DIR__], + [__DIR__ . '/config'], + ]; + } + + public function testRun() : void + { $application = $this->createMock(Application::class); ConsoleRunnerStub::$application = $application; @@ -34,7 +94,7 @@ public function testRun() : void $application->expects(self::once()) ->method('run'); - ConsoleRunnerStub::run($helperSet, []); + ConsoleRunnerStub::run([]); } public function testHasExecuteCommand() : void @@ -88,11 +148,13 @@ public function testHasUpToDateCommand() : void public function testHasDiffCommand() : void { - $this->application->setHelperSet(new HelperSet([ - 'em' => $this->entityManagerHelper, - ])); + $dependencyFactory = $this->createMock(DependencyFactory::class); + $dependencyFactory + ->expects(self::atLeastOnce()) + ->method('hasEntityManager') + ->willReturn(true); - ConsoleRunner::addCommands($this->application); + ConsoleRunner::addCommands($this->application, $dependencyFactory); self::assertTrue($this->application->has('migrations:diff')); } @@ -108,21 +170,28 @@ public function testNotHasDiffCommand() : void public function testCreateApplication() : void { - $helperSet = new HelperSet(); - - $application = ConsoleRunner::createApplication($helperSet); + $application = ConsoleRunner::createApplication(); + $commands = $application->all('migrations'); + self::assertCount(10, $commands); + } - self::assertSame($helperSet, $application->getHelperSet()); + public function testCreateApplicationWithEntityManager() : void + { + $dependencyFactory = $this->createMock(DependencyFactory::class); + $dependencyFactory + ->expects(self::atLeastOnce()) + ->method('hasEntityManager') + ->willReturn(true); + + $application = ConsoleRunner::createApplication([], $dependencyFactory); + $commands = $application->all('migrations'); + self::assertCount(11, $commands); } protected function setUp() : void { parent::setUp(); - - $this->application = new Application(); - $this->entityManagerHelper = $this->getMockBuilder(EntityManagerHelper::class) - ->disableOriginalConstructor() - ->getMock(); + $this->application = new Application(); } } @@ -134,7 +203,7 @@ class ConsoleRunnerStub extends ConsoleRunner /** * @param Command[] $commands */ - public static function createApplication(HelperSet $helperSet, array $commands = []) : Application + public static function createApplication(array $commands = [], ?DependencyFactory $dependencyFactory = null) : Application { return static::$application; } diff --git a/tests/Doctrine/Migrations/Tests/Tools/Console/Helper/ConfigurationHelperTest.php b/tests/Doctrine/Migrations/Tests/Tools/Console/Helper/ConfigurationHelperTest.php deleted file mode 100644 index 1019b6c94c..0000000000 --- a/tests/Doctrine/Migrations/Tests/Tools/Console/Helper/ConfigurationHelperTest.php +++ /dev/null @@ -1,159 +0,0 @@ -input = $this->getMockBuilder(ArrayInput::class) - ->setConstructorArgs([[]]) - ->onlyMethods(['getOption']) - ->getMock(); - - $this->loader = $this->createMock(ConfigurationLoader::class); - $this->configurationHelper = new MigrationsConfigurationHelper($this->loader); - } - - /** - * Test that unsupported file type throws exception - */ - public function testNoAvailableConfigGivesBackEmptyConfig() : void - { - $this->input->method('getOption') - ->with('configuration') - ->willReturn(null); - - $confExpected = new Configuration(); - - $configLoader = $this->createMock(Loader::class); - - $configLoader - ->expects(self::once()) - ->method('load') - ->with([]) - ->willReturn($confExpected); - - $this->loader - ->expects(self::once()) - ->method('getLoader') - ->with('array') - ->willReturn($configLoader); - - $dir = getcwd()?: '.'; - try { - chdir(__DIR__); - $this->configurationHelper->getConfiguration($this->input); - } finally { - chdir($dir); - } - } - - public function testConfigurationHelperFailsToLoadOtherFormat() : void - { - $this->input->method('getOption') - ->with('configuration') - ->will(self::returnValue('testconfig.wrong')); - $this->loader - ->expects(self::once()) - ->method('getLoader') - ->with('wrong') - ->willThrowException(UnknownLoader::new('dummy')); - - $this->expectException(InvalidArgumentException::class); - $this->expectExceptionMessage('Given config file type is not supported'); - - $dir = getcwd()?: '.'; - try { - chdir(__DIR__); - $this->configurationHelper->getConfiguration($this->input); - } finally { - chdir($dir); - } - } - - public function testLoadsFile() : void - { - $confExpected = new Configuration(); - $configLoader = $this->createMock(Loader::class); - - $configLoader - ->expects(self::once()) - ->method('load') - ->with('config.php') - ->willReturn($confExpected); - - $this->loader - ->expects(self::once()) - ->method('getLoader') - ->with('php') - ->willReturn($configLoader); - - $this->input->method('getOption') - ->with('configuration') - ->will(self::returnValue('config.php')); - - $config = $this->configurationHelper->getConfiguration($this->input); - - self::assertSame($config, $confExpected); - } - - public function testLoadsDefaultFile() : void - { - $confExpected = new Configuration(); - $configLoader = $this->createMock(Loader::class); - - $configLoader - ->expects(self::once()) - ->method('load') - ->with('migrations.php') - ->willReturn($confExpected); - - $this->loader - ->expects(self::once()) - ->method('getLoader') - ->with('php') - ->willReturn($configLoader); - - $this->input->method('getOption') - ->with('configuration') - ->willReturn(null); - - $dir = getcwd()?: '.'; - try { - chdir(__DIR__ . '/files'); - $config = $this->configurationHelper->getConfiguration($this->input); - } finally { - chdir($dir); - } - self::assertSame($config, $confExpected); - } -} diff --git a/tests/Doctrine/Migrations/Tests/Tools/Console/Helper/files/config.php b/tests/Doctrine/Migrations/Tests/Tools/Console/Helper/files/config.php deleted file mode 100644 index bea97cb84c..0000000000 --- a/tests/Doctrine/Migrations/Tests/Tools/Console/Helper/files/config.php +++ /dev/null @@ -1,10 +0,0 @@ - 'Doctrine Sandbox Migrations', - 'migrations_namespace' => 'DoctrineMigrationsTest', - 'table_name' => 'doctrine_migration_versions_test', - 'migrations_directory' => 'tests/Doctrine/Migrations/Tests/Tools/Console/Helper/files', -]; diff --git a/tests/Doctrine/Migrations/Tests/Tools/Console/Helper/files/migrations.php b/tests/Doctrine/Migrations/Tests/Tools/Console/Helper/files/migrations.php deleted file mode 100644 index bea97cb84c..0000000000 --- a/tests/Doctrine/Migrations/Tests/Tools/Console/Helper/files/migrations.php +++ /dev/null @@ -1,10 +0,0 @@ - 'Doctrine Sandbox Migrations', - 'migrations_namespace' => 'DoctrineMigrationsTest', - 'table_name' => 'doctrine_migration_versions_test', - 'migrations_directory' => 'tests/Doctrine/Migrations/Tests/Tools/Console/Helper/files', -]; diff --git a/tests/Doctrine/Migrations/Tests/Tools/Console/_files/sqlite-connection.php b/tests/Doctrine/Migrations/Tests/Tools/Console/_files/sqlite-connection.php deleted file mode 100644 index dae54d0076..0000000000 --- a/tests/Doctrine/Migrations/Tests/Tools/Console/_files/sqlite-connection.php +++ /dev/null @@ -1,5 +0,0 @@ - 'pdo_sqlite', 'memory' => true]; diff --git a/tests/Doctrine/Migrations/Tests/Tools/Console/_wrong-config/cli-config.php b/tests/Doctrine/Migrations/Tests/Tools/Console/_wrong-config/cli-config.php new file mode 100644 index 0000000000..fdc5e7bcac --- /dev/null +++ b/tests/Doctrine/Migrations/Tests/Tools/Console/_wrong-config/cli-config.php @@ -0,0 +1,5 @@ +setProxyDir(__DIR__); +$conf->setProxyNamespace('Foo'); +$conf->setMetadataDriverImpl(new PHPDriver('')); + +$conn = DriverManager::getConnection(['driver' => 'pdo_sqlite', 'memory' => true]); + +$em = EntityManager::create($conn, $conf); + +$config = new ConfigurationArray([ + 'name' => 'Doctrine Sandbox Migrations Cli', + 'migrations_paths' => ['DoctrineMigrationsTest' => '.'], +]); + +return DependencyFactory::fromEntityManager($config, new ExistingEntityManager($em)); diff --git a/tests/Doctrine/Migrations/Tests/doctrine-migrations-phpstan-app.php b/tests/Doctrine/Migrations/Tests/doctrine-migrations-phpstan-app.php index a779732c09..c5e0d3b72e 100644 --- a/tests/Doctrine/Migrations/Tests/doctrine-migrations-phpstan-app.php +++ b/tests/Doctrine/Migrations/Tests/doctrine-migrations-phpstan-app.php @@ -6,13 +6,7 @@ use Doctrine\Migrations\Tools\Console\Command\DiffCommand; use Doctrine\Migrations\Tools\Console\ConsoleRunner; -use Symfony\Component\Console\Helper\HelperSet; -use Symfony\Component\Console\Helper\QuestionHelper; require_once __DIR__ . '/../../../../vendor/autoload.php'; - -$helperSet = $helperSet ?? new HelperSet(); -$helperSet->set(new QuestionHelper(), 'question'); - -return ConsoleRunner::createApplication($helperSet, [new DiffCommand()]); +return ConsoleRunner::createApplication([new DiffCommand()]);