Dmitry Kruglov
Dmitry Kruglov

Reputation: 318

ZeroMQ-driven server stops responding after some time

I'm studying how to use ZeroMQ together with EventMachine. To test things out, I wrote a small program in ruby (echo client server) where i used XREQ and XREP sockets. The client application is sending messages to server (consecutive numbers) and getting them back in responce. The interval between sendings is 0.1s. Everything works... until a certain moment. When current number reaches about 400, server just freezes and doesn't respond to client anymore. I tested this on several computers, and still got that strange issue.

The code is pretty straightforward:

server.rb

require 'rubygems'
require 'bundler/setup'
require 'em-zeromq'

Thread.abort_on_exception = true

ADDRESS = 'tcp://127.0.0.1:2091'

class EMServerHandler
  attr_reader :received
  def on_readable(socket, messages)
    client_identity = messages.shift.copy_out_string #getting client identity from the 1st part of the message
    messages.shift #skip the delimeter
    messages.each do |m|
      msg = m.copy_out_string
      puts "server received from #{client_identity}: " + msg
      socket.send_msg("#{client_identity}",'',"#{msg}") #echo message back to the client
    end
  end
end

trap('INT') do
  EM::stop()
end

puts "Program started (with zmq #{ZMQ::Util.version.join('.')})."

EM.run do
EventMachine.epoll
  ctx = EM::ZeroMQ::Context.new(1)  
  server = ctx.bind(ZMQ::XREP, ADDRESS, EMServerHandler.new, {:identity => "server"})
end

client.rb

require 'rubygems'
require 'bundler/setup'
require 'em-zeromq'

Thread.abort_on_exception = true

ADDRESS = 'tcp://127.0.0.1:2091'

class EMClientHandler
  attr_reader :received
  def on_readable(socket, messages)
    messages.shift #skip the delimeter
    messages.each do |m|
      puts "client recieved: " + m.copy_out_string
    end
  end
end

trap('INT') do
  EM::stop()
end

puts "Program started (with zmq #{ZMQ::Util.version.join('.')})."

EM.run do
  EventMachine.epoll
  ctx = EM::ZeroMQ::Context.new(1)
  puts "client"
  puts "enter client name >> "
  identity = gets.strip
  client = ctx.connect(ZMQ::XREQ, ADDRESS, EMClientHandler.new, {:identity => identity})
  client.send_msg('', "hello from client #{identity}")
  count = 0
  EM::PeriodicTimer.new(0.1) do
    client.send_msg('', "#{count += 1}")
  end
end

Please help me figure out the reason for this.

Upvotes: 0

Views: 669

Answers (2)

oo.
oo.

Reputation: 135

Your ZeroMQ context is being reaped by the garbage collector.

You need to move your call to EM::ZeroMQ::Context#new outside of the EM loop.

See the README

Upvotes: 1

Dmitry Kruglov
Dmitry Kruglov

Reputation: 318

At last I figured out that this issue only appeared when using ruby 1.9.3p0, so it feels like this is a bug of that version of ruby. With ruby 1.9.2 everything works like a charm.

Upvotes: 1

Related Questions