diff --git a/core/modules/user/migrations/d6_profile_values.yml b/core/modules/user/migrations/d6_profile_values.yml index 2d6d51d29b..205d598a24 100644 --- a/core/modules/user/migrations/d6_profile_values.yml +++ b/core/modules/user/migrations/d6_profile_values.yml @@ -6,6 +6,7 @@ migration_tags: - Content source: plugin: d6_profile_field_values + migration: user_profile_field process: uid: uid destination: diff --git a/core/modules/user/src/Plugin/migrate/source/d6/ProfileFieldValues.php b/core/modules/user/src/Plugin/migrate/source/d6/ProfileFieldValues.php index ac4929092d..0502daac89 100644 --- a/core/modules/user/src/Plugin/migrate/source/d6/ProfileFieldValues.php +++ b/core/modules/user/src/Plugin/migrate/source/d6/ProfileFieldValues.php @@ -2,18 +2,88 @@ namespace Drupal\user\Plugin\migrate\source\d6; +use Drupal\Core\Entity\EntityManagerInterface; +use Drupal\Core\Plugin\ContainerFactoryPluginInterface; +use Drupal\Core\State\StateInterface; +use Drupal\migrate\Plugin\MigrationInterface; +use Drupal\migrate\Plugin\MigrationPluginManagerInterface; use Drupal\migrate\Row; use Drupal\migrate_drupal\Plugin\migrate\source\DrupalSqlBase; +use Symfony\Component\DependencyInjection\ContainerInterface; /** * Drupal 6 profile fields values source. * + * Available configuration keys: + * - migration: A single migration ID, or an array of migration IDs. + * + * Examples: + * + * This example forces a lookup of profile field names in the migration map + * table in case the profile_field migration needed to change the field + * name due to a name collision or an field name that contains characters + * no longer allowed by Drupal. + * + * @code + * source: + * plugin: d6_profile_field_values + * migration: profile_field + * @endcode + * * @MigrateSource( * id = "d6_profile_field_values", * source_module = "profile" * ) */ -class ProfileFieldValues extends DrupalSqlBase { +class ProfileFieldValues extends DrupalSqlBase implements ContainerFactoryPluginInterface { + + /** + * The migration plugin manager. + * + * @var \Drupal\migrate\Plugin\MigrationPluginManagerInterface + */ + protected $migrationPluginManager; + + /** + * Initialize method. + * + * @param array $configuration + * A configuration array containing information about the plugin instance. + * @param string $plugin_id + * The plugin ID. + * @param mixed $plugin_definition + * The plugin implementation definition. + * @param \Drupal\migrate\Plugin\MigrationInterface $migration + * The migration plugin instance. + * @param \Drupal\Core\State\StateInterface $state + * The state service. + * @param \Drupal\Core\Entity\EntityManagerInterface $entity_manager + * The entity manager. + * @param \Durpal\migrate\Plugin\MigrationPluginManagerInterface $migration_plugin_manager + * The migration plugin manager. + */ + public function __construct(array $configuration, $plugin_id, $plugin_definition, MigrationInterface $migration, StateInterface $state, EntityManagerInterface $entity_manager, MigrationPluginManagerInterface $migration_plugin_manager) { + $configuration += [ + 'migration' => FALSE, + ]; + parent::__construct($configuration, $plugin_id, $plugin_definition, $migration, $state, $entity_manager); + $this->migrationPluginManager = $migration_plugin_manager; + } + + /** + * {@inheritdoc} + */ + public static function create(ContainerInterface $container, array $configuration, $plugin_id, $plugin_definition, MigrationInterface $migration = NULL) { + return new static( + $configuration, + $plugin_id, + $plugin_definition, + $migration, + $container->get('state'), + $container->get('entity.manager'), + $container->get('plugin.manager.migration') + ); + } /** * {@inheritdoc} @@ -39,18 +109,27 @@ public function prepareRow(Row $row) { $results = $query->execute(); foreach ($results as $profile_value) { + // Find the mapped field name for the profile value. + $name = $this->getProfileFieldName($profile_value['fid']); + if ($name === FALSE) { + $name = $profile_value['name']; + } + // Check special case for date. We need to unserialize. if ($profile_value['type'] == 'date') { $date = unserialize($profile_value['value']); $date = date('Y-m-d', mktime(0, 0, 0, $date['month'], $date['day'], $date['year'])); - $row->setSourceProperty($profile_value['name'], ['value' => $date]); + $row->setSourceProperty($name, ['value' => $date]); + $row->setDestinationProperty($name, ['value' => $date]); } elseif ($profile_value['type'] == 'list') { // Explode by newline and comma. - $row->setSourceProperty($profile_value['name'], preg_split("/[\r\n,]+/", $profile_value['value'])); + $row->setSourceProperty($name, preg_split("/[\r\n,]+/", $profile_value['value'])); + $row->setDestinationProperty($name, preg_split("/[\r\n,]+/", $profile_value['value'])); } else { - $row->setSourceProperty($profile_value['name'], [$profile_value['value']]); + $row->setSourceProperty($name, [$profile_value['value']]); + $row->setDestinationProperty($name, [$profile_value['value']]); } } @@ -91,4 +170,42 @@ public function getIds() { ]; } + /** + * Lookup the profile field name based on migration. + * + * @param string $sourceName + * The raw profile field name from the source data. + * + * @return string + * The mapped profile field name + */ + protected function getProfileFieldName($sourceID) { + $migration_ids = $this->configuration['migration']; + if (!is_array($migration_ids)) { + $migration_ids = [$migration_ids]; + } + $sourceValues = [$sourceID]; + /** @var \Drupal\migrate\Plugin\MigrationInterface[] $migrations */ + $migrations = $this->migrationPluginManager->createInstances($migration_ids); + $destination_ids = NULL; + foreach ($migrations as $migration_id => $migration) { + if ($destination_ids = $migration->getIdMap()->lookupDestinationId($sourceValues)) { + break; + } + } + + if (!$destination_ids) { + // Nothing found. + return FALSE; + } + elseif (count($destination_ids) === 2) { + // Destination IDs for fields are an array of the entity type and field + // name in that order. + return $destination_ids[1]; + } + + // Return the first found destination ID. + return reset($destination_ids); + } + }