Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Catch Exceptions thrown during authentication #35

Merged
merged 4 commits into from
Nov 25, 2015
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
23 changes: 21 additions & 2 deletions object-cache.php
Original file line number Diff line number Diff line change
Expand Up @@ -714,7 +714,21 @@ protected function _connect_redis() {
$port = ! empty( $redis_server['port'] ) ? $redis_server['port'] : 6379;
$this->redis->connect( $redis_server['host'], $port, 1, NULL, 100 ); # 1s timeout, 100ms delay between reconnections
if ( ! empty( $redis_server['auth'] ) ) {
$this->redis->auth( $redis_server['auth'] );
try {
$this->redis->auth( $redis_server['auth'] );
// PhpRedis throws an Exception when it fails a server call.
// To prevent WordPress from fataling, we catch the Exception.
} catch ( RedisException $e ) {
try {
$this->last_triggered_error = 'WP Redis: ' . $e->getMessage();
// Be friendly to developers debugging production servers by triggering an error
trigger_error( $this->last_triggered_error, E_USER_WARNING );
} catch( PHPUnit_Framework_Error_Warning $e ) {
// PHPUnit throws an Exception when `trigger_error()` is called.
// To ensure our tests (which expect Exceptions to be caught) continue to run,
// we catch the PHPUnit exception and inspect the RedisException message
}
}
}
$this->is_redis_connected = $this->redis->isConnected();
if ( ! $this->is_redis_connected ) {
Expand All @@ -740,15 +754,20 @@ protected function _call_redis( $method ) {
try {
$retval = call_user_func_array( array( $this->redis, $method ), $arguments );
return $retval;
// PhpRedis throws an Exception when it fails a server call.
// To prevent WordPress from fataling, we catch the Exception.
} catch( RedisException $e ) {
$retry_exception_messages = array( 'socket error on read socket', 'Connection closed', 'Redis server went away' );
$retry_exception_messages = apply_filters( 'wp_redis_retry_exception_messages', $retry_exception_messages );
if ( in_array( $e->getMessage(), $retry_exception_messages ) ) {
try {
$this->last_triggered_error = 'WP Redis: ' . $e->getMessage();
// Be friendly to developers debugging production servers by triggering an error
trigger_error( $this->last_triggered_error, E_USER_WARNING );
} catch( PHPUnit_Framework_Error_Warning $e ) {
// We'll inspect this in the test
// PHPUnit throws an Exception when `trigger_error()` is called.
// To ensure our tests (which expect Exceptions to be caught) continue to run,
// we catch the PHPUnit exception and inspect the RedisException message
}
// Attempt to refresh the connection if it was successfully established once
// $this->is_redis_connected will be set inside _connect_redis()
Expand Down
16 changes: 16 additions & 0 deletions tests/test-cache.php
Original file line number Diff line number Diff line change
Expand Up @@ -87,6 +87,22 @@ public function test_redis_reload_force_cache_flush() {
$this->assertEquals( "SELECT option_value FROM {$wpdb->options} WHERE option_name='wp_redis_do_redis_failback_flush'", $wpdb->last_query );
}

public function test_redis_bad_authentication() {
global $redis_server;
if ( ! class_exists( 'Redis' ) ) {
$this->markTestSkipped( 'PHPRedis extension not available.' );
}
$redis_server['host'] = '127.0.0.1';
$redis_server['port'] = 9999;
$redis_server['auth'] = 'foobar';
$cache = new WP_Object_Cache;
$this->assertEquals( 'WP Redis: Redis server went away', $cache->last_triggered_error );
$this->assertFalse( $cache->is_redis_connected );
// Fails back to the internal object cache
$cache->set( 'foo', 'bar' );
$this->assertEquals( 'bar', $cache->get( 'foo' ) );
}

function test_miss() {
$this->assertEquals(NULL, $this->cache->get(rand_str()));
}
Expand Down