You are here

public function EntityReferenceRevisionsOrphanPurger::deleteOrphansBatchOperation in Entity Reference Revisions 8

Batch operation for checking orphans for a given entity type.

Parameters

string $entity_type_id: The entity type id, for example 'paragraph'.

Iterable|array $context: The context array.

File

src/EntityReferenceRevisionsOrphanPurger.php, line 155

Class

EntityReferenceRevisionsOrphanPurger
Manages orphan composite revision deletion.

Namespace

Drupal\entity_reference_revisions

Code

public function deleteOrphansBatchOperation($entity_type_id, &$context) {
  $composite_type = $this->entityTypeManager
    ->getDefinition($entity_type_id);
  $composite_revision_key = $composite_type
    ->getKey('revision');

  /** @var \Drupal\Core\Entity\ContentEntityStorageInterface $composite_storage */
  $composite_storage = $this->entityTypeManager
    ->getStorage($entity_type_id);
  $batch_size = Settings::get('entity_update_batch_size', 50);
  if (empty($context['sandbox']['total'])) {
    $context['sandbox']['progress'] = 0;
    $context['sandbox']['current_revision_id'] = -1;
    $context['sandbox']['total'] = (int) $composite_storage
      ->getQuery()
      ->allRevisions()
      ->accessCheck(FALSE)
      ->count()
      ->execute();
  }
  if (!isset($context['results'][$entity_type_id])) {
    $context['results'][$entity_type_id]['entity_count'] = 0;
    $context['results'][$entity_type_id]['revision_count'] = 0;
    $context['results'][$entity_type_id]['start'] = $this->time
      ->getRequestTime();
  }

  // Get the next batch of revision ids from the selected entity type.
  // @todo Replace with an entity query on all revisions with a revision ID
  //   condition after https://www.drupal.org/project/drupal/issues/2766135.
  $revision_table = $composite_type
    ->getRevisionTable();
  $entity_revision_ids = $this->database
    ->select($revision_table, 'r')
    ->fields('r', [
    $composite_revision_key,
  ])
    ->range(0, $batch_size)
    ->orderBy($composite_revision_key)
    ->condition($composite_revision_key, $context['sandbox']['current_revision_id'], '>')
    ->execute()
    ->fetchCol();

  /** @var \Drupal\Core\Entity\ContentEntityInterface $composite_revision */
  foreach ($composite_storage
    ->loadMultipleRevisions($entity_revision_ids) as $composite_revision) {
    $context['sandbox']['progress']++;
    $context['sandbox']['current_revision_id'] = $composite_revision
      ->getRevisionId();
    if ($this
      ->isUsed($composite_revision)) {
      continue;
    }
    if ($this
      ->deleteUnusedRevision($composite_revision)) {
      $context['results'][$entity_type_id]['revision_count']++;
      if ($composite_revision
        ->isDefaultRevision()) {
        $context['results'][$entity_type_id]['entity_count']++;
      }
    }
  }

  // This entity type is completed if no new revision ids were found or the
  // total is reached.
  if ($entity_revision_ids && $context['sandbox']['progress'] < $context['sandbox']['total']) {
    $context['finished'] = $context['sandbox']['progress'] / $context['sandbox']['total'];
  }
  else {
    $context['finished'] = 1;
    $context['results'][$entity_type_id]['end'] = $this->time
      ->getRequestTime();
  }
  $interval = $this->dateFormatter
    ->formatInterval($this->time
    ->getRequestTime() - $context['results'][$entity_type_id]['start']);
  $context['message'] = t('Checked @entity_type revisions for orphans: @current of @total in @interval (@deletions deleted)', [
    '@entity_type' => $composite_type
      ->getLabel(),
    '@current' => $context['sandbox']['progress'],
    '@total' => $context['sandbox']['total'],
    '@interval' => $interval,
    '@deletions' => $context['results'][$entity_type_id]['revision_count'],
  ]);
}