function ChainedFastBackend::getMultiple

Same name and namespace in other branches
  1. 11.x core/lib/Drupal/Core/Cache/ChainedFastBackend.php \Drupal\Core\Cache\ChainedFastBackend::getMultiple()

File

core/lib/Drupal/Core/Cache/ChainedFastBackend.php, line 110

Class

ChainedFastBackend
Defines a backend with a fast and a consistent backend chain.

Namespace

Drupal\Core\Cache

Code

public function getMultiple(&$cids, $allow_invalid = FALSE) {
  $cids_copy = $cids;
  $cache = [];
  // If we can determine the time at which the last write to the consistent
  // backend occurred (we might not be able to if it has been recently
  // flushed/restarted), then we can use that to validate items from the fast
  // backend, so try to get those first. Otherwise, we can't assume that
  // anything in the fast backend is valid, so don't even bother fetching
  // from there.
  $last_write_timestamp = $this->getLastWriteTimestamp();
  if ($last_write_timestamp) {
    // Items in the fast backend might be invalid based on their timestamp,
    // but we can't check the timestamp prior to getting the item, which
    // includes unserializing it. However, unserializing an invalid item can
    // throw an exception. For example, a __wakeup() implementation that
    // receives object properties containing references to code or data that
    // no longer exists in the application's current state.
    //
    // Unserializing invalid data, whether it throws an exception or not, is
    // a waste of time, but we only incur it while a cache invalidation has
    // not yet finished propagating to all the fast backend instances.
    //
    // Most cache backend implementations should not wrap their internal
    // get() implementations with a try/catch, because they have no reason to
    // assume that their data is invalid, and doing so would mask
    // unserialization errors of valid data. We do so here, only because the
    // fast backend is non-authoritative, and after discarding its
    // exceptions, we proceed to check the consistent (authoritative) backend
    // and allow exceptions from that to bubble up.
    try {
      $items = $this->fastBackend
        ->getMultiple($cids, $allow_invalid);
    } catch (\Exception $e) {
      $cids = $cids_copy;
      $items = [];
    }
    // Even if items were successfully fetched from the fast backend, they
    // are potentially invalid if older than the last time the bin was
    // written to in the consistent backend, so only keep ones that aren't.
    foreach ($items as $item) {
      if ($item->created < $last_write_timestamp) {
        $cids[array_search($item->cid, $cids_copy)] = $item->cid;
      }
      else {
        $cache[$item->cid] = $item;
      }
    }
  }
  // If there were any cache entries that were not available in the fast
  // backend, retrieve them from the consistent backend and store them in the
  // fast one.
  if ($cids) {
    foreach ($this->consistentBackend
      ->getMultiple($cids, $allow_invalid) as $item) {
      $cache[$item->cid] = $item;
      // Don't write the cache tags to the fast backend as any cache tag
      // invalidation results in an invalidation of the whole fast backend.
      $this->fastBackend
        ->set($item->cid, $item->data, $item->expire);
    }
  }
  return $cache;
}

Buggy or inaccurate documentation? Please file an issue. Need support? Need help programming? Connect with the Drupal community.