El Jueves, 7 de Enero de 2010, Robert Klemme escribi=F3:
I'd personally prefer to use the DRb approach because then you can
actually send typed messages, i.e. whatever information you need. Also,
it was fun to play around with those small test programs. ;-) And you
can have the reader run on any machine in the network.
Hi Robert, I'd like to thank you the help you gave me in this and other=20
threads. Finally I've decided to use posix message queue [*] under Ruby.
The reason is that it allows safely multiple processes or threads using the=
=20
same mqueue to write message (atomic strings) and also having multiple=20
processes reading from the same mqueue which means load-balancing out of th=
e=20
box
The queue size is configurable and the writer/reader can write/read in the=
=20
mqueue in a blocking or non blocking way.
Also, mqueues allow setting a priority to the messages so those messages wi=
th=20
higher priority are fetched first when reading the mqueue.
Posix message queues are just 20-40% slower than pipes in my benchmarks (bu=
t=20
pipes are no multiprocess/thread safe).
I would like to share a working example:
=2D--- posix_mq_reader.rb ------------------------------
require "posix_mq"
# Parameters:
# - queue name (must start by "/")
# - flags:
# - IO::RDONLY =3D> Just to read from the queue
# - IO::CREAT =3D> Create if it doesn't exist
MQ =3D POSIX_MQ.new "/my_mq", IO::RDONLY | IO::CREAT
loop do
# Blocking waiting:
msg =3D MQ.receive.first # It returns an array [message, priority]
puts "messsage received: #{msg}"
end
=2D-----------------------------------------------------
=2D--- posix_mq_writer.rb ------------------------------
require "posix_mq"
# Open with these options:
# - IO::WRONLY =3D> Just to write into the queue.
# - IO::CREAT =3D> Create if it doesn't exist.
# - IO::NONBLOCK =3D> Don't block when writting (instead raise Errno::EAGA=
IN)
MQ =3D POSIX_MQ.new("/my_mq", IO::WRONLY | IO::CREAT | IO::NONBLOCK)
def send(msg)
begin
MQ << msg
rescue Errno::EAGAIN
puts "Errno::EAGAIN received, the queue is full!"
end
end
=2D-----------------------------------------------------
Now the reader and writer can be open multiple times sharing the same mqueu=
e=20
I also tested your suggested solution with DRb with is really nice, but I=20
don't need all the features DRb provides (I just need to pass a simple stri=
ng=20
to other process(es) from multiple workers).
Again thanks a lot to all the people who contributed in this thread, I've=20
learnt a lot.
Best regards.
[*]
http://bogomips.org/ruby_posix_mq/README.html
=2D-=20
I=F1aki Baz Castillo <
[email protected]>