Przeglądaj źródła

add createMonitoredSubscriptionClient method

James Allen 12 lat temu
rodzic
commit
1ee287ed98
1 zmienionych plików z 31 dodań i 0 usunięć
  1. 31 0
      libraries/redis-wrapper/index.coffee

+ 31 - 0
libraries/redis-wrapper/index.coffee

@@ -20,6 +20,7 @@ module.exports = RedisSharelatex =
 			client = require("redis").createClient opts.port, opts.host, standardOpts
 			client = require("redis").createClient opts.port, opts.host, standardOpts
 		return client
 		return client
 		
 		
+	# DO NOT USE. Not robust at all (ends up getting subscribed twice, etc)!
 	createRobustSubscriptionClient: (opts, heartbeatOpts = {}) ->
 	createRobustSubscriptionClient: (opts, heartbeatOpts = {}) ->
 		sub = RedisSharelatex.createClient(opts)
 		sub = RedisSharelatex.createClient(opts)
 		pub = RedisSharelatex.createClient(opts)
 		pub = RedisSharelatex.createClient(opts)
@@ -64,6 +65,36 @@ module.exports = RedisSharelatex =
 		, heartbeatInterval
 		, heartbeatInterval
 		
 		
 		return sub
 		return sub
+	
+	# Attaches an isAlive() method to the subsciption client which returns true
+	# so long as we have had a heartbeat recently.
+	createMonitoredSubscriptionClient: (opts, heartbeatOpts = {}) ->
+		sub = RedisSharelatex.createClient(opts)
+		pub = RedisSharelatex.createClient(opts)
+		
+		heartbeatInterval = heartbeatOpts.heartbeat_interval or 2000 #ms
+		isAliveTimeout = heartbeatOpts.is_alive_timeout or 10000 #ms
+		
+		id = require("crypto").pseudoRandomBytes(16).toString("hex")
+		heartbeatChannel = "heartbeat-#{id}"
+		lastHeartbeat = Date.now()
+		
+		sub.subscribe heartbeatChannel, (error) ->
+			if error?
+				console.error "ERROR: failed to subscribe to #{heartbeatChannel} channel", error
+		sub.on "message", (channel, message) ->
+			if channel == heartbeatChannel
+				lastHeartbeat = Date.now()
+		
+		sub.isAlive = () ->
+			timeSinceLastHeartbeat = Date.now() - lastHeartbeat
+			return (timeSinceLastHeartbeat < isAliveTimeout)
+		
+		setInterval () ->
+			pub.publish heartbeatChannel, "PING"
+		, heartbeatInterval
+		
+		return sub