我需要将数据从关系数据库移动到 Redis 存储中以进行进一步操作。我正在使用带有 Redis 适配器的 Symfony PSR-16 缓存实现,并且我的缓存池中有 2 种类型的项目:
- 第一种缓存项类型将一些哈希映射到关系数据库中记录的主键上,项键看起来像
hash.[the hash value]
,项的值相应地是主键。 - 第二种缓存项类型具有类似于
[table name].[primary key]
现在我需要遍历第一种类型的项目,从中获取主键,并使用这些 PK 获取第二种类型的项目。
使用Symfony缓存是否完全可能,或者我需要使一些服务直接与Redis一起使用以获得更灵活的方法?
是否可以使用正则表达式或标签获取Symfony缓存项?
我刚刚创建了自己的缓存适配器,允许通过模式获取缓存项目,它使用 redis SCAN
指令:
use SymfonyComponentCacheTraits{
RedisProxy, RedisTrait
};
use SymfonyComponentCacheAdapterAbstractAdapter;
use Generator;
/**
* Class RedisAdapter
* Advanced redis adapter with the ability to fetch items using expressions
* @package AppCache
*/
class RedisAdapter extends AbstractAdapter
{
use RedisTrait;
/**
* @var RedisProxy
*/
private $redis;
/**
* @var string
*/
private $namespace;
/**
* @var int
*/
private $namespaceLen;
public function __construct($redisClient, string $namespace = '', int $defaultLifetime = 0)
{
$this->init($redisClient, $namespace, $defaultLifetime);
$this->namespace = $namespace . ':';
$this->namespaceLen = strlen($this->namespace);
}
/**
* Get all cache items by pattern
* @param string $pattern
* @return Generator
*/
public function getItemsByPattern(string $pattern): Generator
{
$iterator = null;
$pattern = $this->prependNamespace($pattern);
while ($keys = $this->redis->scan($iterator, $pattern)) {
foreach ($this->getItems($this->cleanupNamespace($keys)) as $item) {
yield $item;
}
}
}
/**
* Add a namespace to the key
* @param string $key
* @return string
*/
private function prependNamespace(string $key): string
{
return $this->namespace . $key;
}
/**
* Cleanup the namespace
* @param array $keys
* @return array
*/
private function cleanupNamespace(array $keys)
{
$keys = array_map(function ($value) {
return substr($value, $this->namespaceLen);
}, $keys);
return $keys;
}
}