You are here

public function SqlRedirectNotFoundStorage::purgeOldRequests in Redirect 8

Cleans the irrelevant 404 request logs.

Overrides RedirectNotFoundStorageInterface::purgeOldRequests

File

modules/redirect_404/src/SqlRedirectNotFoundStorage.php, line 94

Class

SqlRedirectNotFoundStorage
Provides an SQL implementation for redirect not found storage.

Namespace

Drupal\redirect_404

Code

public function purgeOldRequests() {
  $row_limit = $this->configFactory
    ->get('redirect_404.settings')
    ->get('row_limit');

  // In admin form 0 used as value for 'All' label.
  if ($row_limit == 0) {
    return;
  }
  $query = $this->database
    ->select('redirect_404', 'r404');
  $query
    ->fields('r404', [
    'timestamp',
  ]);

  // On databases known to support log(), use it to calculate a logarithmic
  // scale of the count, to delete records with count of 1-9 first, then
  // 10-99 and so on.
  if ($this->database
    ->driver() == 'mysql' || $this->database
    ->driver() == 'pgsql') {
    $query
      ->addExpression('floor(log(10, count))', 'count_log');
    $query
      ->orderBy('count_log', 'DESC');
  }
  $query
    ->orderBy('timestamp', 'DESC');
  $cutoff = $query
    ->range($row_limit, 1)
    ->execute()
    ->fetchAssoc();
  if (!empty($cutoff)) {

    // Delete records having older timestamp and less visits (on a logarithmic
    // scale) than cutoff.
    $delete_query = $this->database
      ->delete('redirect_404');
    if ($this->database
      ->driver() == 'mysql' || $this->database
      ->driver() == 'pgsql') {

      // Delete rows with same count_log AND older timestamp than cutoff.
      $and_condition = $delete_query
        ->andConditionGroup()
        ->where('floor(log(10, count)) = :count_log2', [
        ':count_log2' => $cutoff['count_log'],
      ])
        ->condition('timestamp', $cutoff['timestamp'], '<=');

      // And delete all the rows with count_log less than the cutoff.
      $condition = $delete_query
        ->orConditionGroup()
        ->where('floor(log(10, count)) < :count_log1', [
        ':count_log1' => $cutoff['count_log'],
      ])
        ->condition($and_condition);
      $delete_query
        ->condition($condition);
    }
    else {
      $delete_query
        ->condition('timestamp', $cutoff['timestamp'], '<=');
    }
    $delete_query
      ->execute();
  }
}