redis-proxy 0.0.1

Sign up to get free protection for your applications and to get access to all the features.
@@ -0,0 +1,2 @@
1
+ *.swp
2
+ *.swo
@@ -0,0 +1,20 @@
1
+ require 'eventmachine'
2
+ require 'redis-proxy/redis_connection'
3
+ require 'redis-proxy/redis_proxy_server'
4
+
5
+ class RedisProxy
6
+
7
+ def self.start(redis_config, host = "0.0.0.0", port = 6379, options = {})
8
+ EventMachine.epoll
9
+ EventMachine.run do
10
+ puts "Starting up redis proxy server"
11
+ EventMachine.start_server host, port, RedisProxyServer, redis_config
12
+ end
13
+ end
14
+
15
+ def self.stop
16
+ puts "Terminating redis proxy server"
17
+ EventMachine.stop
18
+ end
19
+
20
+ end
@@ -0,0 +1,67 @@
1
+ class RedisConnection < EventMachine::Connection
2
+
3
+ def initialize(config, client, request)
4
+ @@nodes = config[:nodes] || []
5
+ @@reconnect_limit = config[:reconnect_limit]
6
+ @@reconnect_delay = config[:reconnect_delay]
7
+ @node_id = 0;
8
+ @last_alive_node = 0;
9
+ @reconnect_count = 0;
10
+
11
+ @client = client
12
+ @request = request
13
+ end
14
+
15
+ def connection_completed
16
+ puts "RedisConnection: connected to redis node: #{@node_id}"
17
+ send_data "*1\r\n$4\r\nINFO\r\n"
18
+ end
19
+
20
+ def receive_data(data)
21
+ if data =~ /role:master/
22
+ puts "RedisConnection: connected to a master node, proxying"
23
+ @last_alive_node = @node_id
24
+ @reconnect_count = 0
25
+ EventMachine.enable_proxy self, @client
26
+
27
+ send_data @request
28
+ else
29
+ puts "RedisConnection: connected to a slave node, reconnecting"
30
+ close_connection
31
+ end
32
+ end
33
+
34
+ def proxy_target_unbound
35
+ puts "RedisConnection: proxy target unbound"
36
+ close_connection
37
+ end
38
+
39
+ def unbind
40
+ puts "RedisConnection: connection unbound"
41
+
42
+ EventMachine.disable_proxy self
43
+
44
+ unless @client_unbind
45
+ @node_id = (@node_id + 1) % @@nodes.count
46
+ @reconnect_count += 1
47
+
48
+ if @reconnect_count == @@reconnect_limit
49
+ @client.close_connection_after_writing
50
+ else
51
+ if @node_id == @last_alive_node
52
+ puts "RedisConnection: finished one reconnect cycle, sleeping before trying again"
53
+ sleep @@reconnect_delay
54
+ end
55
+ reconnect @@nodes[@node_id][:host], @@nodes[@node_id][:port]
56
+ end
57
+ end
58
+ end
59
+
60
+ def client_unbind
61
+ puts "RedisConnection: client unbind"
62
+ EventMachine.disable_proxy self
63
+ @client_unbind = true
64
+ close_connection
65
+ end
66
+
67
+ end
@@ -0,0 +1,25 @@
1
+ class RedisProxyServer < EventMachine::Connection
2
+
3
+ def initialize(redis_config)
4
+ @@redis_config = redis_config
5
+ @@default_node = redis_config[:nodes].first
6
+ end
7
+
8
+ def receive_data(data)
9
+
10
+ if @proxy.nil?
11
+ (@buffer ||= "") << data
12
+ if @buffer =~ /\r\n/
13
+ @proxy = EventMachine.connect @@default_node[:host], @@default_node[:port], RedisConnection, @@redis_config, self, data
14
+ end
15
+ else
16
+ @proxy.send_data data
17
+ end
18
+ end
19
+
20
+ def unbind
21
+ puts "RedisProxy: unbind"
22
+ @proxy.client_unbind
23
+ end
24
+
25
+ end
@@ -0,0 +1,12 @@
1
+ Gem::Specification.new do |s|
2
+ s.name = "redis-proxy"
3
+ s.summary = "A simple redis proxy that handles reconnection and sentinel failover"
4
+ s.version = "0.0.1"
5
+ s.author = "Nan Zhong"
6
+ s.email = "nan@nine27.com"
7
+ s.homepage = 'https://github.com/nanzhong/redis-proxy'
8
+
9
+ s.files = `git ls-files`.split($\)
10
+
11
+ s.add_dependency "eventmachine"
12
+ end
metadata ADDED
@@ -0,0 +1,65 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: redis-proxy
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.0.1
5
+ prerelease:
6
+ platform: ruby
7
+ authors:
8
+ - Nan Zhong
9
+ autorequire:
10
+ bindir: bin
11
+ cert_chain: []
12
+ date: 2012-11-02 00:00:00.000000000 Z
13
+ dependencies:
14
+ - !ruby/object:Gem::Dependency
15
+ name: eventmachine
16
+ requirement: !ruby/object:Gem::Requirement
17
+ none: false
18
+ requirements:
19
+ - - ! '>='
20
+ - !ruby/object:Gem::Version
21
+ version: '0'
22
+ type: :runtime
23
+ prerelease: false
24
+ version_requirements: !ruby/object:Gem::Requirement
25
+ none: false
26
+ requirements:
27
+ - - ! '>='
28
+ - !ruby/object:Gem::Version
29
+ version: '0'
30
+ description:
31
+ email: nan@nine27.com
32
+ executables: []
33
+ extensions: []
34
+ extra_rdoc_files: []
35
+ files:
36
+ - .gitignore
37
+ - lib/redis-proxy.rb
38
+ - lib/redis-proxy/redis_connection.rb
39
+ - lib/redis-proxy/redis_proxy_server.rb
40
+ - redis-proxy.gemspec
41
+ homepage: https://github.com/nanzhong/redis-proxy
42
+ licenses: []
43
+ post_install_message:
44
+ rdoc_options: []
45
+ require_paths:
46
+ - lib
47
+ required_ruby_version: !ruby/object:Gem::Requirement
48
+ none: false
49
+ requirements:
50
+ - - ! '>='
51
+ - !ruby/object:Gem::Version
52
+ version: '0'
53
+ required_rubygems_version: !ruby/object:Gem::Requirement
54
+ none: false
55
+ requirements:
56
+ - - ! '>='
57
+ - !ruby/object:Gem::Version
58
+ version: '0'
59
+ requirements: []
60
+ rubyforge_project:
61
+ rubygems_version: 1.8.24
62
+ signing_key:
63
+ specification_version: 3
64
+ summary: A simple redis proxy that handles reconnection and sentinel failover
65
+ test_files: []