perf: 增加原生缓存
This commit is contained in:
218
vendor/illuminate/redis/Connections/Connection.php
vendored
Normal file
218
vendor/illuminate/redis/Connections/Connection.php
vendored
Normal file
@@ -0,0 +1,218 @@
|
||||
<?php
|
||||
|
||||
namespace Illuminate\Redis\Connections;
|
||||
|
||||
use Closure;
|
||||
use Illuminate\Contracts\Events\Dispatcher;
|
||||
use Illuminate\Redis\Events\CommandExecuted;
|
||||
use Illuminate\Redis\Limiters\ConcurrencyLimiterBuilder;
|
||||
use Illuminate\Redis\Limiters\DurationLimiterBuilder;
|
||||
use Illuminate\Support\Traits\Macroable;
|
||||
|
||||
abstract class Connection
|
||||
{
|
||||
use Macroable {
|
||||
__call as macroCall;
|
||||
}
|
||||
|
||||
/**
|
||||
* The Redis client.
|
||||
*
|
||||
* @var \Redis
|
||||
*/
|
||||
protected $client;
|
||||
|
||||
/**
|
||||
* The Redis connection name.
|
||||
*
|
||||
* @var string|null
|
||||
*/
|
||||
protected $name;
|
||||
|
||||
/**
|
||||
* The event dispatcher instance.
|
||||
*
|
||||
* @var \Illuminate\Contracts\Events\Dispatcher
|
||||
*/
|
||||
protected $events;
|
||||
|
||||
/**
|
||||
* Subscribe to a set of given channels for messages.
|
||||
*
|
||||
* @param array|string $channels
|
||||
* @param \Closure $callback
|
||||
* @param string $method
|
||||
* @return void
|
||||
*/
|
||||
abstract public function createSubscription($channels, Closure $callback, $method = 'subscribe');
|
||||
|
||||
/**
|
||||
* Funnel a callback for a maximum number of simultaneous executions.
|
||||
*
|
||||
* @param string $name
|
||||
* @return \Illuminate\Redis\Limiters\ConcurrencyLimiterBuilder
|
||||
*/
|
||||
public function funnel($name)
|
||||
{
|
||||
return new ConcurrencyLimiterBuilder($this, $name);
|
||||
}
|
||||
|
||||
/**
|
||||
* Throttle a callback for a maximum number of executions over a given duration.
|
||||
*
|
||||
* @param string $name
|
||||
* @return \Illuminate\Redis\Limiters\DurationLimiterBuilder
|
||||
*/
|
||||
public function throttle($name)
|
||||
{
|
||||
return new DurationLimiterBuilder($this, $name);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the underlying Redis client.
|
||||
*
|
||||
* @return mixed
|
||||
*/
|
||||
public function client()
|
||||
{
|
||||
return $this->client;
|
||||
}
|
||||
|
||||
/**
|
||||
* Subscribe to a set of given channels for messages.
|
||||
*
|
||||
* @param array|string $channels
|
||||
* @param \Closure $callback
|
||||
* @return void
|
||||
*/
|
||||
public function subscribe($channels, Closure $callback)
|
||||
{
|
||||
return $this->createSubscription($channels, $callback, __FUNCTION__);
|
||||
}
|
||||
|
||||
/**
|
||||
* Subscribe to a set of given channels with wildcards.
|
||||
*
|
||||
* @param array|string $channels
|
||||
* @param \Closure $callback
|
||||
* @return void
|
||||
*/
|
||||
public function psubscribe($channels, Closure $callback)
|
||||
{
|
||||
return $this->createSubscription($channels, $callback, __FUNCTION__);
|
||||
}
|
||||
|
||||
/**
|
||||
* Run a command against the Redis database.
|
||||
*
|
||||
* @param string $method
|
||||
* @param array $parameters
|
||||
* @return mixed
|
||||
*/
|
||||
public function command($method, array $parameters = [])
|
||||
{
|
||||
$start = microtime(true);
|
||||
|
||||
$result = $this->client->{$method}(...$parameters);
|
||||
|
||||
$time = round((microtime(true) - $start) * 1000, 2);
|
||||
|
||||
if (isset($this->events)) {
|
||||
$this->event(new CommandExecuted($method, $parameters, $time, $this));
|
||||
}
|
||||
|
||||
return $result;
|
||||
}
|
||||
|
||||
/**
|
||||
* Fire the given event if possible.
|
||||
*
|
||||
* @param mixed $event
|
||||
* @return void
|
||||
*/
|
||||
protected function event($event)
|
||||
{
|
||||
$this->events?->dispatch($event);
|
||||
}
|
||||
|
||||
/**
|
||||
* Register a Redis command listener with the connection.
|
||||
*
|
||||
* @param \Closure $callback
|
||||
* @return void
|
||||
*/
|
||||
public function listen(Closure $callback)
|
||||
{
|
||||
$this->events?->listen(CommandExecuted::class, $callback);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the connection name.
|
||||
*
|
||||
* @return string|null
|
||||
*/
|
||||
public function getName()
|
||||
{
|
||||
return $this->name;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the connections name.
|
||||
*
|
||||
* @param string $name
|
||||
* @return $this
|
||||
*/
|
||||
public function setName($name)
|
||||
{
|
||||
$this->name = $name;
|
||||
|
||||
return $this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the event dispatcher used by the connection.
|
||||
*
|
||||
* @return \Illuminate\Contracts\Events\Dispatcher
|
||||
*/
|
||||
public function getEventDispatcher()
|
||||
{
|
||||
return $this->events;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the event dispatcher instance on the connection.
|
||||
*
|
||||
* @param \Illuminate\Contracts\Events\Dispatcher $events
|
||||
* @return void
|
||||
*/
|
||||
public function setEventDispatcher(Dispatcher $events)
|
||||
{
|
||||
$this->events = $events;
|
||||
}
|
||||
|
||||
/**
|
||||
* Unset the event dispatcher instance on the connection.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function unsetEventDispatcher()
|
||||
{
|
||||
$this->events = null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Pass other method calls down to the underlying client.
|
||||
*
|
||||
* @param string $method
|
||||
* @param array $parameters
|
||||
* @return mixed
|
||||
*/
|
||||
public function __call($method, $parameters)
|
||||
{
|
||||
if (static::hasMacro($method)) {
|
||||
return $this->macroCall($method, $parameters);
|
||||
}
|
||||
|
||||
return $this->command($method, $parameters);
|
||||
}
|
||||
}
|
||||
183
vendor/illuminate/redis/Connections/PacksPhpRedisValues.php
vendored
Normal file
183
vendor/illuminate/redis/Connections/PacksPhpRedisValues.php
vendored
Normal file
@@ -0,0 +1,183 @@
|
||||
<?php
|
||||
|
||||
namespace Illuminate\Redis\Connections;
|
||||
|
||||
use Redis;
|
||||
use RuntimeException;
|
||||
use UnexpectedValueException;
|
||||
|
||||
trait PacksPhpRedisValues
|
||||
{
|
||||
/**
|
||||
* Indicates if Redis supports packing.
|
||||
*
|
||||
* @var bool|null
|
||||
*/
|
||||
protected $supportsPacking;
|
||||
|
||||
/**
|
||||
* Indicates if Redis supports LZF compression.
|
||||
*
|
||||
* @var bool|null
|
||||
*/
|
||||
protected $supportsLzf;
|
||||
|
||||
/**
|
||||
* Indicates if Redis supports Zstd compression.
|
||||
*
|
||||
* @var bool|null
|
||||
*/
|
||||
protected $supportsZstd;
|
||||
|
||||
/**
|
||||
* Prepares the given values to be used with the `eval` command, including serialization and compression.
|
||||
*
|
||||
* @param array<int|string,string> $values
|
||||
* @return array<int|string,string>
|
||||
*/
|
||||
public function pack(array $values): array
|
||||
{
|
||||
if (empty($values)) {
|
||||
return $values;
|
||||
}
|
||||
|
||||
if ($this->supportsPacking()) {
|
||||
return array_map([$this->client, '_pack'], $values);
|
||||
}
|
||||
|
||||
if ($this->compressed()) {
|
||||
if ($this->supportsLzf() && $this->lzfCompressed()) {
|
||||
if (! function_exists('lzf_compress')) {
|
||||
throw new RuntimeException("'lzf' extension required to call 'lzf_compress'.");
|
||||
}
|
||||
|
||||
$processor = function ($value) {
|
||||
return \lzf_compress($this->client->_serialize($value));
|
||||
};
|
||||
} elseif ($this->supportsZstd() && $this->zstdCompressed()) {
|
||||
if (! function_exists('zstd_compress')) {
|
||||
throw new RuntimeException("'zstd' extension required to call 'zstd_compress'.");
|
||||
}
|
||||
|
||||
$compressionLevel = $this->client->getOption(Redis::OPT_COMPRESSION_LEVEL);
|
||||
|
||||
$processor = function ($value) use ($compressionLevel) {
|
||||
return \zstd_compress(
|
||||
$this->client->_serialize($value),
|
||||
$compressionLevel === 0 ? Redis::COMPRESSION_ZSTD_DEFAULT : $compressionLevel
|
||||
);
|
||||
};
|
||||
} else {
|
||||
throw new UnexpectedValueException(sprintf(
|
||||
'Unsupported phpredis compression in use [%d].',
|
||||
$this->client->getOption(Redis::OPT_COMPRESSION)
|
||||
));
|
||||
}
|
||||
} else {
|
||||
$processor = function ($value) {
|
||||
return $this->client->_serialize($value);
|
||||
};
|
||||
}
|
||||
|
||||
return array_map($processor, $values);
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if compression is enabled.
|
||||
*
|
||||
* @return bool
|
||||
*/
|
||||
public function compressed(): bool
|
||||
{
|
||||
return defined('Redis::OPT_COMPRESSION') &&
|
||||
$this->client->getOption(Redis::OPT_COMPRESSION) !== Redis::COMPRESSION_NONE;
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if LZF compression is enabled.
|
||||
*
|
||||
* @return bool
|
||||
*/
|
||||
public function lzfCompressed(): bool
|
||||
{
|
||||
return defined('Redis::COMPRESSION_LZF') &&
|
||||
$this->client->getOption(Redis::OPT_COMPRESSION) === Redis::COMPRESSION_LZF;
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if ZSTD compression is enabled.
|
||||
*
|
||||
* @return bool
|
||||
*/
|
||||
public function zstdCompressed(): bool
|
||||
{
|
||||
return defined('Redis::COMPRESSION_ZSTD') &&
|
||||
$this->client->getOption(Redis::OPT_COMPRESSION) === Redis::COMPRESSION_ZSTD;
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if LZ4 compression is enabled.
|
||||
*
|
||||
* @return bool
|
||||
*/
|
||||
public function lz4Compressed(): bool
|
||||
{
|
||||
return defined('Redis::COMPRESSION_LZ4') &&
|
||||
$this->client->getOption(Redis::OPT_COMPRESSION) === Redis::COMPRESSION_LZ4;
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if the current PhpRedis extension version supports packing.
|
||||
*
|
||||
* @return bool
|
||||
*/
|
||||
protected function supportsPacking(): bool
|
||||
{
|
||||
if ($this->supportsPacking === null) {
|
||||
$this->supportsPacking = $this->phpRedisVersionAtLeast('5.3.5');
|
||||
}
|
||||
|
||||
return $this->supportsPacking;
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if the current PhpRedis extension version supports LZF compression.
|
||||
*
|
||||
* @return bool
|
||||
*/
|
||||
protected function supportsLzf(): bool
|
||||
{
|
||||
if ($this->supportsLzf === null) {
|
||||
$this->supportsLzf = $this->phpRedisVersionAtLeast('4.3.0');
|
||||
}
|
||||
|
||||
return $this->supportsLzf;
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if the current PhpRedis extension version supports Zstd compression.
|
||||
*
|
||||
* @return bool
|
||||
*/
|
||||
protected function supportsZstd(): bool
|
||||
{
|
||||
if ($this->supportsZstd === null) {
|
||||
$this->supportsZstd = $this->phpRedisVersionAtLeast('5.1.0');
|
||||
}
|
||||
|
||||
return $this->supportsZstd;
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if the PhpRedis extension version is at least the given version.
|
||||
*
|
||||
* @param string $version
|
||||
* @return bool
|
||||
*/
|
||||
protected function phpRedisVersionAtLeast(string $version): bool
|
||||
{
|
||||
$phpredisVersion = phpversion('redis');
|
||||
|
||||
return $phpredisVersion !== false && version_compare($phpredisVersion, $version, '>=');
|
||||
}
|
||||
}
|
||||
24
vendor/illuminate/redis/Connections/PhpRedisClusterConnection.php
vendored
Normal file
24
vendor/illuminate/redis/Connections/PhpRedisClusterConnection.php
vendored
Normal file
@@ -0,0 +1,24 @@
|
||||
<?php
|
||||
|
||||
namespace Illuminate\Redis\Connections;
|
||||
|
||||
class PhpRedisClusterConnection extends PhpRedisConnection
|
||||
{
|
||||
/**
|
||||
* Flush the selected Redis database on all master nodes.
|
||||
*
|
||||
* @return mixed
|
||||
*/
|
||||
public function flushdb()
|
||||
{
|
||||
$arguments = func_get_args();
|
||||
|
||||
$async = strtoupper((string) ($arguments[0] ?? null)) === 'ASYNC';
|
||||
|
||||
foreach ($this->client->_masters() as $master) {
|
||||
$async
|
||||
? $this->command('rawCommand', [$master, 'flushdb', 'async'])
|
||||
: $this->command('flushdb', [$master]);
|
||||
}
|
||||
}
|
||||
}
|
||||
567
vendor/illuminate/redis/Connections/PhpRedisConnection.php
vendored
Normal file
567
vendor/illuminate/redis/Connections/PhpRedisConnection.php
vendored
Normal file
@@ -0,0 +1,567 @@
|
||||
<?php
|
||||
|
||||
namespace Illuminate\Redis\Connections;
|
||||
|
||||
use Closure;
|
||||
use Illuminate\Contracts\Redis\Connection as ConnectionContract;
|
||||
use Illuminate\Support\Arr;
|
||||
use Redis;
|
||||
use RedisException;
|
||||
|
||||
/**
|
||||
* @mixin \Redis
|
||||
*/
|
||||
class PhpRedisConnection extends Connection implements ConnectionContract
|
||||
{
|
||||
use PacksPhpRedisValues;
|
||||
|
||||
/**
|
||||
* The connection creation callback.
|
||||
*
|
||||
* @var callable
|
||||
*/
|
||||
protected $connector;
|
||||
|
||||
/**
|
||||
* The connection configuration array.
|
||||
*
|
||||
* @var array
|
||||
*/
|
||||
protected $config;
|
||||
|
||||
/**
|
||||
* Create a new PhpRedis connection.
|
||||
*
|
||||
* @param \Redis $client
|
||||
* @param callable|null $connector
|
||||
* @param array $config
|
||||
* @return void
|
||||
*/
|
||||
public function __construct($client, callable $connector = null, array $config = [])
|
||||
{
|
||||
$this->client = $client;
|
||||
$this->config = $config;
|
||||
$this->connector = $connector;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the value of the given key.
|
||||
*
|
||||
* @param string $key
|
||||
* @return string|null
|
||||
*/
|
||||
public function get($key)
|
||||
{
|
||||
$result = $this->command('get', [$key]);
|
||||
|
||||
return $result !== false ? $result : null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the values of all the given keys.
|
||||
*
|
||||
* @param array $keys
|
||||
* @return array
|
||||
*/
|
||||
public function mget(array $keys)
|
||||
{
|
||||
return array_map(function ($value) {
|
||||
return $value !== false ? $value : null;
|
||||
}, $this->command('mget', [$keys]));
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the string value in the argument as the value of the key.
|
||||
*
|
||||
* @param string $key
|
||||
* @param mixed $value
|
||||
* @param string|null $expireResolution
|
||||
* @param int|null $expireTTL
|
||||
* @param string|null $flag
|
||||
* @return bool
|
||||
*/
|
||||
public function set($key, $value, $expireResolution = null, $expireTTL = null, $flag = null)
|
||||
{
|
||||
return $this->command('set', [
|
||||
$key,
|
||||
$value,
|
||||
$expireResolution ? [$flag, $expireResolution => $expireTTL] : null,
|
||||
]);
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the given key if it doesn't exist.
|
||||
*
|
||||
* @param string $key
|
||||
* @param string $value
|
||||
* @return int
|
||||
*/
|
||||
public function setnx($key, $value)
|
||||
{
|
||||
return (int) $this->command('setnx', [$key, $value]);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the value of the given hash fields.
|
||||
*
|
||||
* @param string $key
|
||||
* @param mixed ...$dictionary
|
||||
* @return array
|
||||
*/
|
||||
public function hmget($key, ...$dictionary)
|
||||
{
|
||||
if (count($dictionary) === 1) {
|
||||
$dictionary = $dictionary[0];
|
||||
}
|
||||
|
||||
return array_values($this->command('hmget', [$key, $dictionary]));
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the given hash fields to their respective values.
|
||||
*
|
||||
* @param string $key
|
||||
* @param mixed ...$dictionary
|
||||
* @return int
|
||||
*/
|
||||
public function hmset($key, ...$dictionary)
|
||||
{
|
||||
if (count($dictionary) === 1) {
|
||||
$dictionary = $dictionary[0];
|
||||
} else {
|
||||
$input = collect($dictionary);
|
||||
|
||||
$dictionary = $input->nth(2)->combine($input->nth(2, 1))->toArray();
|
||||
}
|
||||
|
||||
return $this->command('hmset', [$key, $dictionary]);
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the given hash field if it doesn't exist.
|
||||
*
|
||||
* @param string $hash
|
||||
* @param string $key
|
||||
* @param string $value
|
||||
* @return int
|
||||
*/
|
||||
public function hsetnx($hash, $key, $value)
|
||||
{
|
||||
return (int) $this->command('hsetnx', [$hash, $key, $value]);
|
||||
}
|
||||
|
||||
/**
|
||||
* Removes the first count occurrences of the value element from the list.
|
||||
*
|
||||
* @param string $key
|
||||
* @param int $count
|
||||
* @param mixed $value
|
||||
* @return int|false
|
||||
*/
|
||||
public function lrem($key, $count, $value)
|
||||
{
|
||||
return $this->command('lrem', [$key, $value, $count]);
|
||||
}
|
||||
|
||||
/**
|
||||
* Removes and returns the first element of the list stored at key.
|
||||
*
|
||||
* @param mixed ...$arguments
|
||||
* @return array|null
|
||||
*/
|
||||
public function blpop(...$arguments)
|
||||
{
|
||||
$result = $this->command('blpop', $arguments);
|
||||
|
||||
return empty($result) ? null : $result;
|
||||
}
|
||||
|
||||
/**
|
||||
* Removes and returns the last element of the list stored at key.
|
||||
*
|
||||
* @param mixed ...$arguments
|
||||
* @return array|null
|
||||
*/
|
||||
public function brpop(...$arguments)
|
||||
{
|
||||
$result = $this->command('brpop', $arguments);
|
||||
|
||||
return empty($result) ? null : $result;
|
||||
}
|
||||
|
||||
/**
|
||||
* Removes and returns a random element from the set value at key.
|
||||
*
|
||||
* @param string $key
|
||||
* @param int|null $count
|
||||
* @return mixed|false
|
||||
*/
|
||||
public function spop($key, $count = 1)
|
||||
{
|
||||
return $this->command('spop', func_get_args());
|
||||
}
|
||||
|
||||
/**
|
||||
* Add one or more members to a sorted set or update its score if it already exists.
|
||||
*
|
||||
* @param string $key
|
||||
* @param mixed ...$dictionary
|
||||
* @return int
|
||||
*/
|
||||
public function zadd($key, ...$dictionary)
|
||||
{
|
||||
if (is_array(end($dictionary))) {
|
||||
foreach (array_pop($dictionary) as $member => $score) {
|
||||
$dictionary[] = $score;
|
||||
$dictionary[] = $member;
|
||||
}
|
||||
}
|
||||
|
||||
$options = [];
|
||||
|
||||
foreach (array_slice($dictionary, 0, 3) as $i => $value) {
|
||||
if (in_array($value, ['nx', 'xx', 'ch', 'incr', 'gt', 'lt', 'NX', 'XX', 'CH', 'INCR', 'GT', 'LT'], true)) {
|
||||
$options[] = $value;
|
||||
|
||||
unset($dictionary[$i]);
|
||||
}
|
||||
}
|
||||
|
||||
return $this->command('zadd', array_merge([$key], [$options], array_values($dictionary)));
|
||||
}
|
||||
|
||||
/**
|
||||
* Return elements with score between $min and $max.
|
||||
*
|
||||
* @param string $key
|
||||
* @param mixed $min
|
||||
* @param mixed $max
|
||||
* @param array $options
|
||||
* @return array
|
||||
*/
|
||||
public function zrangebyscore($key, $min, $max, $options = [])
|
||||
{
|
||||
if (isset($options['limit']) && Arr::isAssoc($options['limit'])) {
|
||||
$options['limit'] = [
|
||||
$options['limit']['offset'],
|
||||
$options['limit']['count'],
|
||||
];
|
||||
}
|
||||
|
||||
return $this->command('zRangeByScore', [$key, $min, $max, $options]);
|
||||
}
|
||||
|
||||
/**
|
||||
* Return elements with score between $min and $max.
|
||||
*
|
||||
* @param string $key
|
||||
* @param mixed $min
|
||||
* @param mixed $max
|
||||
* @param array $options
|
||||
* @return array
|
||||
*/
|
||||
public function zrevrangebyscore($key, $min, $max, $options = [])
|
||||
{
|
||||
if (isset($options['limit']) && Arr::isAssoc($options['limit'])) {
|
||||
$options['limit'] = [
|
||||
$options['limit']['offset'],
|
||||
$options['limit']['count'],
|
||||
];
|
||||
}
|
||||
|
||||
return $this->command('zRevRangeByScore', [$key, $min, $max, $options]);
|
||||
}
|
||||
|
||||
/**
|
||||
* Find the intersection between sets and store in a new set.
|
||||
*
|
||||
* @param string $output
|
||||
* @param array $keys
|
||||
* @param array $options
|
||||
* @return int
|
||||
*/
|
||||
public function zinterstore($output, $keys, $options = [])
|
||||
{
|
||||
return $this->command('zinterstore', [$output, $keys,
|
||||
$options['weights'] ?? null,
|
||||
$options['aggregate'] ?? 'sum',
|
||||
]);
|
||||
}
|
||||
|
||||
/**
|
||||
* Find the union between sets and store in a new set.
|
||||
*
|
||||
* @param string $output
|
||||
* @param array $keys
|
||||
* @param array $options
|
||||
* @return int
|
||||
*/
|
||||
public function zunionstore($output, $keys, $options = [])
|
||||
{
|
||||
return $this->command('zunionstore', [$output, $keys,
|
||||
$options['weights'] ?? null,
|
||||
$options['aggregate'] ?? 'sum',
|
||||
]);
|
||||
}
|
||||
|
||||
/**
|
||||
* Scans all keys based on options.
|
||||
*
|
||||
* @param mixed $cursor
|
||||
* @param array $options
|
||||
* @return mixed
|
||||
*/
|
||||
public function scan($cursor, $options = [])
|
||||
{
|
||||
$result = $this->client->scan($cursor,
|
||||
$options['match'] ?? '*',
|
||||
$options['count'] ?? 10
|
||||
);
|
||||
|
||||
if ($result === false) {
|
||||
$result = [];
|
||||
}
|
||||
|
||||
return $cursor === 0 && empty($result) ? false : [$cursor, $result];
|
||||
}
|
||||
|
||||
/**
|
||||
* Scans the given set for all values based on options.
|
||||
*
|
||||
* @param string $key
|
||||
* @param mixed $cursor
|
||||
* @param array $options
|
||||
* @return mixed
|
||||
*/
|
||||
public function zscan($key, $cursor, $options = [])
|
||||
{
|
||||
$result = $this->client->zscan($key, $cursor,
|
||||
$options['match'] ?? '*',
|
||||
$options['count'] ?? 10
|
||||
);
|
||||
|
||||
if ($result === false) {
|
||||
$result = [];
|
||||
}
|
||||
|
||||
return $cursor === 0 && empty($result) ? false : [$cursor, $result];
|
||||
}
|
||||
|
||||
/**
|
||||
* Scans the given hash for all values based on options.
|
||||
*
|
||||
* @param string $key
|
||||
* @param mixed $cursor
|
||||
* @param array $options
|
||||
* @return mixed
|
||||
*/
|
||||
public function hscan($key, $cursor, $options = [])
|
||||
{
|
||||
$result = $this->client->hscan($key, $cursor,
|
||||
$options['match'] ?? '*',
|
||||
$options['count'] ?? 10
|
||||
);
|
||||
|
||||
if ($result === false) {
|
||||
$result = [];
|
||||
}
|
||||
|
||||
return $cursor === 0 && empty($result) ? false : [$cursor, $result];
|
||||
}
|
||||
|
||||
/**
|
||||
* Scans the given set for all values based on options.
|
||||
*
|
||||
* @param string $key
|
||||
* @param mixed $cursor
|
||||
* @param array $options
|
||||
* @return mixed
|
||||
*/
|
||||
public function sscan($key, $cursor, $options = [])
|
||||
{
|
||||
$result = $this->client->sscan($key, $cursor,
|
||||
$options['match'] ?? '*',
|
||||
$options['count'] ?? 10
|
||||
);
|
||||
|
||||
if ($result === false) {
|
||||
$result = [];
|
||||
}
|
||||
|
||||
return $cursor === 0 && empty($result) ? false : [$cursor, $result];
|
||||
}
|
||||
|
||||
/**
|
||||
* Execute commands in a pipeline.
|
||||
*
|
||||
* @param callable|null $callback
|
||||
* @return \Redis|array
|
||||
*/
|
||||
public function pipeline(callable $callback = null)
|
||||
{
|
||||
$pipeline = $this->client()->pipeline();
|
||||
|
||||
return is_null($callback)
|
||||
? $pipeline
|
||||
: tap($pipeline, $callback)->exec();
|
||||
}
|
||||
|
||||
/**
|
||||
* Execute commands in a transaction.
|
||||
*
|
||||
* @param callable|null $callback
|
||||
* @return \Redis|array
|
||||
*/
|
||||
public function transaction(callable $callback = null)
|
||||
{
|
||||
$transaction = $this->client()->multi();
|
||||
|
||||
return is_null($callback)
|
||||
? $transaction
|
||||
: tap($transaction, $callback)->exec();
|
||||
}
|
||||
|
||||
/**
|
||||
* Evaluate a LUA script serverside, from the SHA1 hash of the script instead of the script itself.
|
||||
*
|
||||
* @param string $script
|
||||
* @param int $numkeys
|
||||
* @param mixed ...$arguments
|
||||
* @return mixed
|
||||
*/
|
||||
public function evalsha($script, $numkeys, ...$arguments)
|
||||
{
|
||||
return $this->command('evalsha', [
|
||||
$this->script('load', $script), $arguments, $numkeys,
|
||||
]);
|
||||
}
|
||||
|
||||
/**
|
||||
* Evaluate a script and return its result.
|
||||
*
|
||||
* @param string $script
|
||||
* @param int $numberOfKeys
|
||||
* @param dynamic ...$arguments
|
||||
* @return mixed
|
||||
*/
|
||||
public function eval($script, $numberOfKeys, ...$arguments)
|
||||
{
|
||||
return $this->command('eval', [$script, $arguments, $numberOfKeys]);
|
||||
}
|
||||
|
||||
/**
|
||||
* Subscribe to a set of given channels for messages.
|
||||
*
|
||||
* @param array|string $channels
|
||||
* @param \Closure $callback
|
||||
* @return void
|
||||
*/
|
||||
public function subscribe($channels, Closure $callback)
|
||||
{
|
||||
$this->client->subscribe((array) $channels, function ($redis, $channel, $message) use ($callback) {
|
||||
$callback($message, $channel);
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Subscribe to a set of given channels with wildcards.
|
||||
*
|
||||
* @param array|string $channels
|
||||
* @param \Closure $callback
|
||||
* @return void
|
||||
*/
|
||||
public function psubscribe($channels, Closure $callback)
|
||||
{
|
||||
$this->client->psubscribe((array) $channels, function ($redis, $pattern, $channel, $message) use ($callback) {
|
||||
$callback($message, $channel);
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Subscribe to a set of given channels for messages.
|
||||
*
|
||||
* @param array|string $channels
|
||||
* @param \Closure $callback
|
||||
* @param string $method
|
||||
* @return void
|
||||
*/
|
||||
public function createSubscription($channels, Closure $callback, $method = 'subscribe')
|
||||
{
|
||||
//
|
||||
}
|
||||
|
||||
/**
|
||||
* Flush the selected Redis database.
|
||||
*
|
||||
* @return mixed
|
||||
*/
|
||||
public function flushdb()
|
||||
{
|
||||
$arguments = func_get_args();
|
||||
|
||||
if (strtoupper((string) ($arguments[0] ?? null)) === 'ASYNC') {
|
||||
return $this->command('flushdb', [true]);
|
||||
}
|
||||
|
||||
return $this->command('flushdb');
|
||||
}
|
||||
|
||||
/**
|
||||
* Execute a raw command.
|
||||
*
|
||||
* @param array $parameters
|
||||
* @return mixed
|
||||
*/
|
||||
public function executeRaw(array $parameters)
|
||||
{
|
||||
return $this->command('rawCommand', $parameters);
|
||||
}
|
||||
|
||||
/**
|
||||
* Run a command against the Redis database.
|
||||
*
|
||||
* @param string $method
|
||||
* @param array $parameters
|
||||
* @return mixed
|
||||
*
|
||||
* @throws \RedisException
|
||||
*/
|
||||
public function command($method, array $parameters = [])
|
||||
{
|
||||
try {
|
||||
return parent::command($method, $parameters);
|
||||
} catch (RedisException $e) {
|
||||
foreach (['went away', 'socket', 'read error on connection'] as $errorMessage) {
|
||||
if (str_contains($e->getMessage(), $errorMessage)) {
|
||||
$this->client = $this->connector ? call_user_func($this->connector) : $this->client;
|
||||
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
throw $e;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Disconnects from the Redis instance.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function disconnect()
|
||||
{
|
||||
$this->client->close();
|
||||
}
|
||||
|
||||
/**
|
||||
* Pass other method calls down to the underlying client.
|
||||
*
|
||||
* @param string $method
|
||||
* @param array $parameters
|
||||
* @return mixed
|
||||
*/
|
||||
public function __call($method, $parameters)
|
||||
{
|
||||
return parent::__call(strtolower($method), $parameters);
|
||||
}
|
||||
}
|
||||
25
vendor/illuminate/redis/Connections/PredisClusterConnection.php
vendored
Normal file
25
vendor/illuminate/redis/Connections/PredisClusterConnection.php
vendored
Normal file
@@ -0,0 +1,25 @@
|
||||
<?php
|
||||
|
||||
namespace Illuminate\Redis\Connections;
|
||||
|
||||
use Predis\Command\Redis\FLUSHDB;
|
||||
use Predis\Command\ServerFlushDatabase;
|
||||
|
||||
class PredisClusterConnection extends PredisConnection
|
||||
{
|
||||
/**
|
||||
* Flush the selected Redis database on all cluster nodes.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function flushdb()
|
||||
{
|
||||
$command = class_exists(ServerFlushDatabase::class)
|
||||
? ServerFlushDatabase::class
|
||||
: FLUSHDB::class;
|
||||
|
||||
foreach ($this->client as $node) {
|
||||
$node->executeCommand(tap(new $command)->setArguments(func_get_args()));
|
||||
}
|
||||
}
|
||||
}
|
||||
53
vendor/illuminate/redis/Connections/PredisConnection.php
vendored
Normal file
53
vendor/illuminate/redis/Connections/PredisConnection.php
vendored
Normal file
@@ -0,0 +1,53 @@
|
||||
<?php
|
||||
|
||||
namespace Illuminate\Redis\Connections;
|
||||
|
||||
use Closure;
|
||||
use Illuminate\Contracts\Redis\Connection as ConnectionContract;
|
||||
|
||||
/**
|
||||
* @mixin \Predis\Client
|
||||
*/
|
||||
class PredisConnection extends Connection implements ConnectionContract
|
||||
{
|
||||
/**
|
||||
* The Predis client.
|
||||
*
|
||||
* @var \Predis\Client
|
||||
*/
|
||||
protected $client;
|
||||
|
||||
/**
|
||||
* Create a new Predis connection.
|
||||
*
|
||||
* @param \Predis\Client $client
|
||||
* @return void
|
||||
*/
|
||||
public function __construct($client)
|
||||
{
|
||||
$this->client = $client;
|
||||
}
|
||||
|
||||
/**
|
||||
* Subscribe to a set of given channels for messages.
|
||||
*
|
||||
* @param array|string $channels
|
||||
* @param \Closure $callback
|
||||
* @param string $method
|
||||
* @return void
|
||||
*/
|
||||
public function createSubscription($channels, Closure $callback, $method = 'subscribe')
|
||||
{
|
||||
$loop = $this->pubSubLoop();
|
||||
|
||||
$loop->{$method}(...array_values((array) $channels));
|
||||
|
||||
foreach ($loop as $message) {
|
||||
if ($message->kind === 'message' || $message->kind === 'pmessage') {
|
||||
$callback($message->payload, $message->channel);
|
||||
}
|
||||
}
|
||||
|
||||
unset($loop);
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user