migrations
migrations copied to clipboard
[Command] Calling `DoctrineCommand` multiple times with multiple connections
Bug Report
| Q | A |
|---|---|
| BC Break | no |
| Version | 3.6.0 |
Summary
Using Multiple Database in a single Symfony Application. We need to trigger the MigrateCommand x times for x databases from a cron/hook when deploying a new version.
Current behavior
Note : Running this Command with the
--connoption seems to not works. So we use the--emoption.
When calling the MigrateCommand multiple times FROM Command/Code the connection will be:
-
getted https://github.com/doctrine/migrations/blob/2f4b14968df1cb1c6e8beb724d142c4a8ddf2842/lib/Doctrine/Migrations/Tools/Console/Command/MigrateCommand.php#L132
-
AND setted at the same time (if undefined) https://github.com/doctrine/migrations/blob/2f4b14968df1cb1c6e8beb724d142c4a8ddf2842/lib/Doctrine/Migrations/DependencyFactory.php#L158-L168
Because of this, the connection will always be the first "implemented". In the end, calling this command in a loop and changing the connection/entityManager at each iteration won't work as untended.
How to reproduce
- Have multiple connections
- Have multiple EntityManagers
- Run this command
<?php
namespace App\Command;
use Symfony\Component\Console\Attribute\AsCommand;
use Symfony\Component\Console\Command\Command;
use Symfony\Component\Console\Input\ArrayInput;
use Symfony\Component\Console\Input\InputInterface;
use Symfony\Component\Console\Output\OutputInterface;
#[AsCommand(
name: 'app:test',
)]
class TestCommand extends Command
{
protected function execute(InputInterface $input, OutputInterface $output): int
{
$entityManagers = [
'client1',
'client2',
];
foreach ($entityManagers as $entityManager) {
$commandToCall = $this->getApplication()->find('d:m:m');
$commandInput = new ArrayInput(
[
'--em' => $entityManager,
]
);
$commandToCall->run(
$commandInput,
$output
);
}
return Command::SUCCESS;
}
}
- Output
a. First loop :
WARNING! You are about to execute a migration in database "client1" that could result in schema changes and data loss. Are you sure you wish to continue? (yes/no) [yes]b. Second loop:WARNING! You are about to execute a migration in database "client1" that could result in schema changes and data loss. Are you sure you wish to continue? (yes/no) [yes]
Expected behavior
The first loop should be client1 and the second client2.
Note : Running single command from CLI is working
php bin/console d:m:m --em=client1orphp bin/console d:m:m --em=client2
Doctrine config
php bin/console debug:config doctrine
Current configuration for extension with alias "doctrine"
=========================================================
doctrine:
orm:
resolve_target_entities:
Allsoftware\SymfonyBundle\Model\FichierInterface: App\Entity\Fichier
Allsoftware\SymfonyBundle\Model\DossierInterface: App\Entity\Dossier
auto_generate_proxy_classes: true
entity_managers:
default:
dql:
string_functions:
regexp: DoctrineExtensions\Query\Mysql\Regexp
numeric_functions: { }
datetime_functions: { }
naming_strategy: doctrine.orm.naming_strategy.underscore_number_aware
auto_mapping: true
mappings:
App:
is_bundle: false
type: attribute
dir: /var/www/html/src/Entity
prefix: App\Entity
alias: App
mapping: true
AllsoftwareSymfonyBundle:
type: attribute
dir: src/Model
prefix: Allsoftware\SymfonyBundle\Model
mapping: true
query_cache_driver:
type: null
result_cache_driver:
type: null
class_metadata_factory_name: Doctrine\ORM\Mapping\ClassMetadataFactory
default_repository_class: Doctrine\ORM\EntityRepository
quote_strategy: doctrine.orm.quote_strategy.default
entity_listener_resolver: null
repository_factory: doctrine.orm.container_repository_factory
schema_ignore_classes: { }
report_fields_where_declared: false
validate_xml_mapping: false
hydrators: { }
filters: { }
client1:
dql:
string_functions:
regexp: DoctrineExtensions\Query\Mysql\Regexp
numeric_functions: { }
datetime_functions: { }
naming_strategy: doctrine.orm.naming_strategy.underscore_number_aware
mappings:
App:
is_bundle: false
type: attribute
dir: /var/www/html/src/Entity
prefix: App\Entity
alias: App
mapping: true
connection: client1
query_cache_driver:
type: null
result_cache_driver:
type: null
class_metadata_factory_name: Doctrine\ORM\Mapping\ClassMetadataFactory
default_repository_class: Doctrine\ORM\EntityRepository
auto_mapping: false
quote_strategy: doctrine.orm.quote_strategy.default
entity_listener_resolver: null
repository_factory: doctrine.orm.container_repository_factory
schema_ignore_classes: { }
report_fields_where_declared: false
validate_xml_mapping: false
hydrators: { }
filters: { }
client2:
dql:
string_functions:
regexp: DoctrineExtensions\Query\Mysql\Regexp
numeric_functions: { }
datetime_functions: { }
naming_strategy: doctrine.orm.naming_strategy.underscore_number_aware
mappings:
App:
is_bundle: false
type: attribute
dir: /var/www/html/src/Entity
prefix: App\Entity
alias: App
mapping: true
connection: client2
query_cache_driver:
type: null
result_cache_driver:
type: null
class_metadata_factory_name: Doctrine\ORM\Mapping\ClassMetadataFactory
default_repository_class: Doctrine\ORM\EntityRepository
auto_mapping: false
quote_strategy: doctrine.orm.quote_strategy.default
entity_listener_resolver: null
repository_factory: doctrine.orm.container_repository_factory
schema_ignore_classes: { }
report_fields_where_declared: false
validate_xml_mapping: false
hydrators: { }
filters: { }
enable_lazy_ghost_objects: false
proxy_dir: /var/www/html/var/cache/dev/doctrine/orm/Proxies
proxy_namespace: Proxies
controller_resolver:
enabled: true
auto_mapping: true
evict_cache: false
dbal:
connections:
default:
url: '%env(resolve:DATABASE_URL)%'
wrapper_class: App\DBAL\MultiDbConnectionWrapper
driver: pdo_mysql
logging: true
profiling: true
profiling_collect_backtrace: false
profiling_collect_schema_errors: true
options: { }
mapping_types: { }
default_table_options: { }
schema_manager_factory: doctrine.dbal.legacy_schema_manager_factory
slaves: { }
replicas: { }
client1:
url: 'mysql://root:root@mysqlhost:3306/nils_client1'
driver: pdo_mysql
logging: true
profiling: true
profiling_collect_backtrace: false
profiling_collect_schema_errors: true
options: { }
mapping_types: { }
default_table_options: { }
schema_manager_factory: doctrine.dbal.legacy_schema_manager_factory
slaves: { }
replicas: { }
client2:
url: 'mysql://root:root@mysqlhost:3306/nils_client2'
driver: pdo_mysql
logging: true
profiling: true
profiling_collect_backtrace: false
profiling_collect_schema_errors: true
options: { }
mapping_types: { }
default_table_options: { }
schema_manager_factory: doctrine.dbal.legacy_schema_manager_factory
slaves: { }
replicas: { }
types:
uuid:
class: Ramsey\Uuid\Doctrine\UuidType
driver_schemes: { }