class BackdropDatabaseCache implements BackdropCacheInterface {
protected $bin;
function __construct(string $bin) {
if ($bin != 'cache') {
$bin = 'cache_' . $bin;
}
$this->bin = $bin;
if (!function_exists('db_query') || backdrop_get_bootstrap_phase() < BACKDROP_BOOTSTRAP_DATABASE) {
backdrop_bootstrap(BACKDROP_BOOTSTRAP_DATABASE, FALSE);
}
}
function get(string $cid) {
$cids = array($cid);
$cache = $this->getMultiple($cids);
return reset($cache);
}
function getMultiple(array &$cids) {
try {
$result = db_query('SELECT cid, data, created, expire, serialized FROM {' . db_escape_table($this->bin) . '} WHERE cid IN (:cids)', array(':cids' => $cids));
$cache = array();
foreach ($result as $item) {
$item = $this->prepareItem($item);
if ($item) {
$cache[$item->cid] = $item;
}
}
$cids = array_diff($cids, array_keys($cache));
return $cache;
}
catch (Exception $e) {
return array();
}
}
protected function prepareItem($cache) {
if (!isset($cache->data)) {
return FALSE;
}
if ($cache->serialized) {
$cache->data = unserialize($cache->data);
}
return $cache;
}
function set(string $cid, $data, int $expire = CACHE_PERMANENT) {
$fields = array(
'serialized' => 0,
'created' => REQUEST_TIME,
'expire' => $expire,
);
if (!is_string($data)) {
$fields['data'] = serialize($data);
$fields['serialized'] = 1;
}
else {
$fields['data'] = $data;
$fields['serialized'] = 0;
}
try {
db_merge($this->bin)
->key(array('cid' => $cid))
->fields($fields)
->execute();
}
catch (Exception $e) {
}
}
function delete(string $cid) {
db_delete($this->bin)
->condition('cid', $cid)
->execute();
}
function deleteMultiple(array $cids) {
do {
db_delete($this->bin)
->condition('cid', array_splice($cids, 0, 1000), 'IN')
->execute();
}
while (count($cids));
}
function deletePrefix(string $prefix) {
db_delete($this->bin)
->condition('cid', db_like($prefix) . '%', 'LIKE')
->execute();
}
function flush() {
db_truncate($this->bin)->execute();
}
function garbageCollection() {
db_delete($this->bin)
->condition('expire', CACHE_PERMANENT, '<>')
->condition('expire', REQUEST_TIME, '<')
->execute();
}
function isEmpty() {
$this->garbageCollection();
$query = db_select($this->bin);
$query->addExpression('1');
$result = $query->range(0, 1)
->execute()
->fetchField();
return empty($result);
}
}