diff --git a/core/lib/Drupal/Core/Entity/EntityDefinitionUpdateManager.php b/core/lib/Drupal/Core/Entity/EntityDefinitionUpdateManager.php index 197e4a44ac0..9c115881035 100644 --- a/core/lib/Drupal/Core/Entity/EntityDefinitionUpdateManager.php +++ b/core/lib/Drupal/Core/Entity/EntityDefinitionUpdateManager.php @@ -70,12 +70,6 @@ class EntityDefinitionUpdateManager implements EntityDefinitionUpdateManagerInte $summary = array(); foreach ($this->getChangeList() as $entity_type_id => $change_list) { - // Process entity type definition changes. - if (!empty($change_list['entity_type']) && $change_list['entity_type'] == static::DEFINITION_UPDATED) { - $entity_type = $this->entityManager->getDefinition($entity_type_id); - $summary[$entity_type_id][] = $this->t('Update the %entity_type entity type.', array('%entity_type' => $entity_type->getLabel())); - } - // Process field storage definition changes. if (!empty($change_list['field_storage_definitions'])) { $storage_definitions = $this->entityManager->getFieldStorageDefinitions($entity_type_id); @@ -97,6 +91,11 @@ class EntityDefinitionUpdateManager implements EntityDefinitionUpdateManagerInte } } } + // Process entity type definition changes. + if (!empty($change_list['entity_type']) && $change_list['entity_type'] == static::DEFINITION_UPDATED) { + $entity_type = $this->entityManager->getDefinition($entity_type_id); + $summary[$entity_type_id][] = $this->t('Update the %entity_type entity type.', array('%entity_type' => $entity_type->getLabel())); + } } return $summary; @@ -107,13 +106,6 @@ class EntityDefinitionUpdateManager implements EntityDefinitionUpdateManagerInte */ public function applyUpdates() { foreach ($this->getChangeList() as $entity_type_id => $change_list) { - // Process entity type definition changes. - if (!empty($change_list['entity_type']) && $change_list['entity_type'] == static::DEFINITION_UPDATED) { - $entity_type = $this->entityManager->getDefinition($entity_type_id); - $original = $this->entityManager->getLastInstalledDefinition($entity_type_id); - $this->entityManager->onEntityTypeUpdate($entity_type, $original); - } - // Process field storage definition changes. if (!empty($change_list['field_storage_definitions'])) { $storage_definitions = $this->entityManager->getFieldStorageDefinitions($entity_type_id); @@ -135,6 +127,15 @@ class EntityDefinitionUpdateManager implements EntityDefinitionUpdateManagerInte } } } + // Process entity type definition changes after storage definitions ones + // as entity type updates might create base fields as well. That way, if + // both occur at the same time it does not lead to problems due to the + // base field creation being applied twice. + if (!empty($change_list['entity_type']) && $change_list['entity_type'] == static::DEFINITION_UPDATED) { + $entity_type = $this->entityManager->getDefinition($entity_type_id); + $original = $this->entityManager->getLastInstalledDefinition($entity_type_id); + $this->entityManager->onEntityTypeUpdate($entity_type, $original); + } } } diff --git a/core/modules/system/src/Tests/Entity/EntityDefinitionUpdateTest.php b/core/modules/system/src/Tests/Entity/EntityDefinitionUpdateTest.php index 96c75832bce..84a25af8b37 100644 --- a/core/modules/system/src/Tests/Entity/EntityDefinitionUpdateTest.php +++ b/core/modules/system/src/Tests/Entity/EntityDefinitionUpdateTest.php @@ -477,6 +477,25 @@ class EntityDefinitionUpdateTest extends EntityUnitTestBase { $this->assertTrue($event_subscriber->hasEventFired(EntityTypeEvents::DELETE), 'Entity type delete event successfully dispatched.'); } + /** + * Tests updating entity schema and creating a base field at the same time when there are no existing entities. + */ + public function testEntityTypeSchemaUpdateAndBaseFieldCreateWithoutData() { + $this->updateEntityTypeToRevisionable(); + $this->addBaseField(); + // Entity type updates create base fields as well, thus make sure doing both + // at the same time does not lead to errors due to the base field being + // created twice. + try { + $this->entityDefinitionUpdateManager->applyUpdates(); + $this->pass('Successfully updated entity schema and created base field at the same time.'); + } + catch (\Exception $e) { + $this->fail('Successfully updated entity schema and created base field at the same time.'); + throw $e; + } + } + /** * Updates the 'entity_test_update' entity type to revisionable. */