mirror of
https://github.com/Seldaek/monolog.git
synced 2025-02-22 05:52:31 +01:00
Adds ability to cap log size in redis
100% backward compatible, defaults to not capping collection size. Additional constructor param of $capSize added which will ensure logs list is treated as a FILO queue Test coverage on new functionality
This commit is contained in:
parent
bfe5081735
commit
050694291e
@ -29,14 +29,16 @@ class RedisHandler extends AbstractProcessingHandler
|
|||||||
{
|
{
|
||||||
private $redisClient;
|
private $redisClient;
|
||||||
private $redisKey;
|
private $redisKey;
|
||||||
|
protected $capSize;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @param \Predis\Client|\Redis $redis The redis instance
|
* @param \Predis\Client|\Redis $redis The redis instance
|
||||||
* @param string $key The key name to push records to
|
* @param string $key The key name to push records to
|
||||||
* @param integer $level The minimum logging level at which this handler will be triggered
|
* @param integer $level The minimum logging level at which this handler will be triggered
|
||||||
* @param boolean $bubble Whether the messages that are handled can bubble up the stack or not
|
* @param boolean $bubble Whether the messages that are handled can bubble up the stack or not
|
||||||
|
* @param integer $capSize Number of entries to limit list size to
|
||||||
*/
|
*/
|
||||||
public function __construct($redis, $key, $level = Logger::DEBUG, $bubble = true)
|
public function __construct($redis, $key, $level = Logger::DEBUG, $bubble = true, $capSize = false)
|
||||||
{
|
{
|
||||||
if (!(($redis instanceof \Predis\Client) || ($redis instanceof \Redis))) {
|
if (!(($redis instanceof \Predis\Client) || ($redis instanceof \Redis))) {
|
||||||
throw new \InvalidArgumentException('Predis\Client or Redis instance required');
|
throw new \InvalidArgumentException('Predis\Client or Redis instance required');
|
||||||
@ -44,13 +46,44 @@ class RedisHandler extends AbstractProcessingHandler
|
|||||||
|
|
||||||
$this->redisClient = $redis;
|
$this->redisClient = $redis;
|
||||||
$this->redisKey = $key;
|
$this->redisKey = $key;
|
||||||
|
$this->capSize = $capSize;
|
||||||
|
|
||||||
parent::__construct($level, $bubble);
|
parent::__construct($level, $bubble);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* {@inheritDoc}
|
||||||
|
*/
|
||||||
protected function write(array $record)
|
protected function write(array $record)
|
||||||
{
|
{
|
||||||
$this->redisClient->rpush($this->redisKey, $record["formatted"]);
|
if ($this->capSize)
|
||||||
|
{
|
||||||
|
$this->writeCapped($record);
|
||||||
|
} else {
|
||||||
|
$this->redisClient->rpush($this->redisKey, $record["formatted"]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Write and cap the collection
|
||||||
|
* Writes the record to the redis list and caps its
|
||||||
|
*
|
||||||
|
* @param array $record associative record array
|
||||||
|
* @return void
|
||||||
|
*/
|
||||||
|
protected function writeCapped(array $record)
|
||||||
|
{
|
||||||
|
if($this->redisClient instanceof \Redis) {
|
||||||
|
$this->redisClient->multi()
|
||||||
|
->lpush($this->redisKey, $record["formatted"])
|
||||||
|
->ltrim($this->redisKey, 0, $this->capSize)
|
||||||
|
->execute();
|
||||||
|
} else {
|
||||||
|
$this->redisClient->transaction(function($tx) use($record) {
|
||||||
|
$tx->lpush($this->redisKey, $record["formatted"]);
|
||||||
|
$tx->ltrim($this->redisKey, 0, $this->capSize);
|
||||||
|
});
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -68,4 +68,61 @@ class RedisHandlerTest extends TestCase
|
|||||||
$handler->setFormatter(new LineFormatter("%message%"));
|
$handler->setFormatter(new LineFormatter("%message%"));
|
||||||
$handler->handle($record);
|
$handler->handle($record);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public function testRedisHandleCapped()
|
||||||
|
{
|
||||||
|
$redis = $this->getMock('Redis', array('multi', 'lpush', 'ltrim', 'execute'));
|
||||||
|
|
||||||
|
// Redis uses multi
|
||||||
|
$redis->expects($this->once())
|
||||||
|
->method('multi')
|
||||||
|
->will($this->returnSelf());
|
||||||
|
|
||||||
|
$redis->expects($this->once())
|
||||||
|
->method('lpush')
|
||||||
|
->will($this->returnSelf());
|
||||||
|
|
||||||
|
$redis->expects($this->once())
|
||||||
|
->method('ltrim')
|
||||||
|
->will($this->returnSelf());
|
||||||
|
|
||||||
|
$redis->expects($this->once())
|
||||||
|
->method('execute')
|
||||||
|
->will($this->returnSelf());
|
||||||
|
|
||||||
|
$record = $this->getRecord(Logger::WARNING, 'test', array('data' => new \stdClass, 'foo' => 34));
|
||||||
|
|
||||||
|
$handler = new RedisHandler($redis, 'key', Logger::DEBUG, true, 10);
|
||||||
|
$handler->setFormatter(new LineFormatter("%message%"));
|
||||||
|
$handler->handle($record);
|
||||||
|
}
|
||||||
|
|
||||||
|
public function testPredisHandleCapped()
|
||||||
|
{
|
||||||
|
$redis = $this->getMock('Predis\Client', array('transaction'));
|
||||||
|
|
||||||
|
// Redis uses multi
|
||||||
|
$redis->expects($this->once())
|
||||||
|
->method('transaction')
|
||||||
|
->will($this->returnCallback(function($cb){
|
||||||
|
|
||||||
|
$redisTransaction = $this->getMock('Predis\Client', array('lpush', 'ltrim'));
|
||||||
|
|
||||||
|
$redisTransaction->expects($this->once())
|
||||||
|
->method('lpush')
|
||||||
|
->will($this->returnSelf());
|
||||||
|
|
||||||
|
$redisTransaction->expects($this->once())
|
||||||
|
->method('ltrim')
|
||||||
|
->will($this->returnSelf());
|
||||||
|
|
||||||
|
$cb($redisTransaction);
|
||||||
|
}));
|
||||||
|
|
||||||
|
$record = $this->getRecord(Logger::WARNING, 'test', array('data' => new \stdClass, 'foo' => 34));
|
||||||
|
|
||||||
|
$handler = new RedisHandler($redis, 'key', Logger::DEBUG, true, 10);
|
||||||
|
$handler->setFormatter(new LineFormatter("%message%"));
|
||||||
|
$handler->handle($record);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
Loading…
x
Reference in New Issue
Block a user