public function APDQCache::getMultiple in Asynchronous Prefetch Database Query Cache 7
Implements DrupalCacheInterface::getMultiple().
We handle garbage collection differently; this method is reimplemented only to remove a call to the garbageCollection() method.
Overrides DrupalDatabaseCache::getMultiple
File
- ./
apdqc.cache.inc, line 328 - Extends Drupal's default database cache so async queries happen.
Class
- APDQCache
- A pretty darn quick cache implementation of Drupal's default cache backend.
Code
public function getMultiple(&$cids) {
try {
$gc_frequency = variable_get('cache_garbage_collection_frequency', CACHE_GARBAGE_COLLECTION_FREQUENCY);
if (empty($gc_frequency)) {
// Garbage collection necessary when enforcing a minimum cache lifetime.
$this
->garbageCollection($this->bin);
}
$query_cids = $cids;
$prefetch = array();
$result = array();
if (variable_get('cache_bootstrap_prefetch', CACHE_BOOTSTRAP_PREFETCH) || defined('APDQC_PREFETCH') && variable_get('apdqc_prefetch', APDQC_PREFETCH)) {
$prefetch = apdqc_async_data(FALSE, $this->bin, $cids);
$query_cids = array_diff($cids, array_keys($prefetch));
$prefetch = array_values($prefetch);
}
$result = array();
if (!empty($query_cids)) {
// Build query.
$query = Database::getConnection()
->prefixTables("SELECT cid, data, created, expire, serialized FROM {" . db_escape_table($this->bin) . "}");
// If this is the cache_bootstrap bin and the cid is variables, get
// the bootstrap_modules & lookup_cache ids as well.
if ($this->bin === 'cache_bootstrap' && $query_cids[0] === 'variables' && count($query_cids) == 1) {
$query_cids[] = 'bootstrap_modules';
$query_cids[] = 'lookup_cache';
$query_cids[] = 'system_list';
$query_cids[] = 'module_implements';
$bootstrap = TRUE;
}
foreach ($query_cids as $cid) {
$escaped_cids[] = apdqc_escape_string($cid);
}
$escaped_cids = "'" . implode("', '", $escaped_cids) . "'";
$query .= " WHERE cid IN ({$escaped_cids})";
// Run query.
$result = apdqc_query(array(
$this->bin,
), $query_cids, $query, array(
'fetch_all' => TRUE,
));
}
if (is_string($result) && $result === 'NO DB') {
// When serving cached pages, the overhead of using db_select() was
// found to add around 30% overhead to the request. Since $this->bin is
// a variable, this means the call to db_query() here uses a
// concatenated string. This is highly discouraged under any other
// circumstances, and is used here only due to the performance overhead
// we would incur otherwise. When serving an uncached page, the overhead
// of using db_select() is a much smaller proportion of the request.
// @codingStandardsIgnoreLine
$result = db_query('SELECT cid, data, created, expire, serialized FROM {' . db_escape_table($this->bin) . '} WHERE cid IN (:cids)', array(
':cids' => $cids,
));
}
else {
$result = array_merge($result, $prefetch);
}
$cache = array();
if (!empty($result)) {
foreach ($result as $item) {
// Skip empty items.
if (empty($item)) {
continue;
}
if (!empty($bootstrap) && is_array($item) && ($item['cid'] === 'bootstrap_modules' || $item['cid'] === 'lookup_cache' || $item['cid'] === 'system_list' || $item['cid'] === 'module_implements')) {
$local_storage =& drupal_static('apdqc_async_data');
$item['bin'] = $this->bin;
$local_storage[$this->bin][$item['cid']] = $item;
continue;
}
// Convert to an object to mirror db_query if needed.
if (is_array($item)) {
$item = (object) $item;
}
$item = $this
->prepareItem($item);
if ($item) {
$cache[$item->cid] = $item;
}
}
}
$cids = array_diff($cids, array_keys($cache));
return $cache;
} catch (Exception $e) {
// If the database is never going to be available, cache requests should
// return FALSE in order to allow exception handling to occur.
return array();
}
}