Sha256: f02b05ea90818e553280799ee4ac46735db071c7d1d507f3d048c4a0aee2f03a

Contents?: true

Size: 1.97 KB

Versions: 16

Compression:

Stored size: 1.97 KB

Contents

module RedisFailover
  # NodeWatcher periodically monitors a specific redis node for its availability.
  # NodeWatcher instances periodically report a redis node's current state
  # to the NodeManager for proper handling.
  class NodeWatcher
    include Util

    # Time to sleep before checking on the monitored node's status.
    WATCHER_SLEEP_TIME = 2

    # Creates a new instance.
    #
    # @param [NodeManager] manager the node manager
    # @param [Node] node the node to watch
    # @param [Integer] max_failures the max failues before reporting node as down
    def initialize(manager, node, max_failures)
      @manager = manager
      @node = node
      @max_failures = max_failures
      @monitor_thread = nil
      @done = false
    end

    # Starts the node watcher.
    #
    # @note this method returns immediately and causes monitoring to be
    #   performed in a new background thread
    def watch
      @monitor_thread ||= Thread.new { monitor_node }
      self
    end

    # Performs a graceful shutdown of this watcher.
    def shutdown
      @done = true
      @node.wakeup
      @monitor_thread.join if @monitor_thread
    rescue
      # best effort
    end

    private

    # Periodically monitors the redis node and reports state changes to
    # the {RedisFailover::NodeManager}.
    def monitor_node
      failures = 0

      loop do
        begin
          return if @done
          sleep(WATCHER_SLEEP_TIME)
          @node.ping
          failures = 0

          if @node.syncing_with_master?
            notify(:syncing)
          else
            notify(:available)
            @node.wait
          end
        rescue NodeUnavailableError
          failures += 1
          if failures >= @max_failures
            notify(:unavailable)
            failures = 0
          end
        end
      end
    end

    # Notifies the manager of a node's state.
    #
    # @param [Symbol] state the node's state
    def notify(state)
      @manager.notify_state(@node, state)
    end
  end
end

Version data entries

16 entries across 16 versions & 2 rubygems

Version Path
nogara-redis_failover-0.9.1 lib/redis_failover/node_watcher.rb
redis_failover-0.9.1 lib/redis_failover/node_watcher.rb
nogara-redis_failover-0.9.0 lib/redis_failover/node_watcher.rb
redis_failover-0.9.0 lib/redis_failover/node_watcher.rb
nogara-redis_failover-0.8.11 lib/redis_failover/node_watcher.rb
nogara-redis_failover-0.8.10 lib/redis_failover/node_watcher.rb
nogara-redis_failover-0.8.9 lib/redis_failover/node_watcher.rb
redis_failover-0.8.9 lib/redis_failover/node_watcher.rb
redis_failover-0.8.8 lib/redis_failover/node_watcher.rb
redis_failover-0.8.7 lib/redis_failover/node_watcher.rb
redis_failover-0.8.6 lib/redis_failover/node_watcher.rb
redis_failover-0.8.5 lib/redis_failover/node_watcher.rb
redis_failover-0.8.4 lib/redis_failover/node_watcher.rb
redis_failover-0.8.3 lib/redis_failover/node_watcher.rb
redis_failover-0.8.2 lib/redis_failover/node_watcher.rb
redis_failover-0.8.1 lib/redis_failover/node_watcher.rb