You are here

public function ContentEntityCdfNormalizer::getReferencedFields in Acquia Content Hub 8

Get entity reference fields.

Get the fields from a given entity and add them to the given content hub entity object.

Parameters

\Drupal\Core\Entity\ContentEntityInterface $entity: The Drupal Entity.

array $context: Additional Context such as the account.

Return value

\Drupal\Core\Entity\ContentEntityInterface[] All referenced entities.

1 call to ContentEntityCdfNormalizer::getReferencedFields()
ContentEntityCdfNormalizer::getMultilevelReferencedFields in src/Normalizer/ContentEntityCdfNormalizer.php
Get multilevel entity reference fields.

File

src/Normalizer/ContentEntityCdfNormalizer.php, line 690

Class

ContentEntityCdfNormalizer
Converts the Drupal entity object to a Acquia Content Hub CDF array.

Namespace

Drupal\acquia_contenthub\Normalizer

Code

public function getReferencedFields(ContentEntityInterface $entity, array $context = []) {

  /** @var \Drupal\acquia_contenthub\Entity\ContentHubEntityTypeConfig[] $content_hub_entity_type_ids */
  $content_hub_entity_type_ids = $this->entityManager
    ->getContentHubEntityTypeConfigurationEntities();
  $bundle_key = $this->entityTypeManager
    ->getDefinition($entity
    ->getEntityTypeId())
    ->getKey('bundle');

  // Check if 'entity_embed' exists.
  $exists_entity_embed = \Drupal::moduleHandler()
    ->moduleExists('entity_embed');
  $referenced_entities = [];

  // If it is a taxonomy term, check for parent information.
  // We are considering the parent does not change per translation.
  // https://www.drupal.org/node/2543726
  if ($entity
    ->getEntityTypeId() === 'taxonomy_term') {
    $parents = $this->entityTypeManager
      ->getStorage('taxonomy_term')
      ->loadParents($entity
      ->id());
    foreach ($parents as $parent) {
      if ($this->entityManager
        ->isEligibleDependency($parent)) {
        $referenced_entities[$parent
          ->uuid()] = $parent;
      }
    }
  }

  // Ignore the entity ID and revision ID.
  // Excluded comes here.
  $excluded_fields = $this
    ->excludedProperties($entity);

  // Find all languages for the current entity.
  $languages = $entity
    ->getTranslationLanguages();

  // Go through all the languages.
  // We have to iterate over the entity translations and add all the
  // references that are included per translation.
  foreach ($languages as $language) {
    $langcode = $language
      ->getId();
    $localized_entity = $entity
      ->getTranslation($langcode);

    /** @var \Drupal\Core\Field\FieldItemListInterface[] $fields */
    $fields = $localized_entity
      ->getFields();
    foreach ($fields as $name => $field) {

      // Continue if this is an excluded field or the current user does not
      // have access to view it.
      $context['account'] = isset($context['account']) ? $context['account'] : NULL;
      if (in_array($field
        ->getFieldDefinition()
        ->getName(), $excluded_fields) || !$field
        ->access('view', $context['account']) || $name === $bundle_key) {
        continue;
      }
      if ($exists_entity_embed) {
        $entity_embed_handler = new ContentHubEntityEmbedHandler($field);
        if ($entity_embed_handler
          ->isProcessable()) {
          $embed_entities = $entity_embed_handler
            ->getReferencedEntities();
          foreach ($embed_entities as $uuid => $embedded_entity) {
            $referenced_entities[$uuid] = $embedded_entity;
          }
        }
      }
      if ($link_field = ContentHubEntityLinkFieldHandler::load($field)
        ->validate()) {
        $link_entities = $link_field
          ->getReferencedEntities($field
          ->getValue());
        foreach ($link_entities as $link_entity) {
          $referenced_entities[$link_entity
            ->uuid()] = $link_entity;
        }
      }
      if ($field instanceof EntityReferenceFieldItemListInterface && !$field
        ->isEmpty()) {

        // Before checking each individual target entity, verify if we can
        // skip all of them at once by checking if none of the target bundles
        // are set to be exported in Content Hub configuration.
        $skip_entities = FALSE;
        $settings = $field
          ->getFieldDefinition()
          ->getSettings();
        $target_type = isset($settings['target_type']) ? $settings['target_type'] : NULL;
        if (isset($settings['handler_settings']['target_bundles'])) {
          $target_bundles = $settings['handler_settings']['target_bundles'];
        }
        else {

          // Certain field types such as file or user do not have target
          // bundles. In this case, we have to inspect each referenced entity
          // and collect all their bundles.
          $target_bundles = [];
          $field_entities = $field
            ->referencedEntities();
          foreach ($field_entities as $field_entity) {
            if ($field_entity instanceof EntityInterface) {
              $target_bundles[] = $field_entity
                ->bundle();
            }
          }
          $target_bundles = array_unique($target_bundles);
          if (empty($target_bundles)) {

            // In cases where there is no bundle defined, the default bundle
            // name is the same as the entity type, e.g. 'file', 'user'.
            $target_bundles = [
              $target_type,
            ];
          }
        }

        // Compare the list of bundles with the bundles set to be exportable
        // in the Content Hub Entity configuration form.
        if (!empty($target_type)) {
          $skip_entities = TRUE;
          foreach ($target_bundles as $target_bundle) {

            // If there is at least one bundle set to be exportable, it means
            // this field cannot be skipped.
            if (isset($content_hub_entity_type_ids[$target_type]) && $content_hub_entity_type_ids[$target_type]
              ->isEnableIndex($target_bundle)) {
              $skip_entities = FALSE;
              break;
            }
          }
        }

        // Check each referenced entity to see if it should be exported.
        if (!$skip_entities) {
          $field_entities = $field
            ->referencedEntities();
          foreach ($field_entities as $field_entity) {
            if ($this->entityManager
              ->isEligibleDependency($field_entity)) {

              /** @var \Drupal\Core\Entity\EntityInterface[] $referenced_entities */
              $referenced_entities[$field_entity
                ->uuid()] = $field_entity;
            }
          }
        }
      }
    }
  }
  return $referenced_entities;
}