I'm trying to write a server connection in Ruby that will spawn a thread to handle incoming connections. This thread will then interpret the incoming data, then place some instructions in a queue to be processed by the main program loop at its convenience. However, I seem to have some issues with the queue processing, as the program seems to either block somewhere, or the main loop just stops working unexpectedly. It's somewhat hard to explain so, here is the listen method for my server socket:
def listen
@socket = TCPServer.open(@ip, @port)
while @looping do
puts "Waiting for socket accept"
server = @socket.accept
puts "Socket accepted"
serverloop = Thread.new do
puts "Waiting for response"
response = server.read
puts "Command received: #{response}"
parse_command(response)
puts "Response complete"
end
processloop = Thread.new do
while @looping do
process_command_queue
process_response_queue
end
end
if interrupted
exit
end
end
end
def process_command_queue
puts "In the command queue"
if @command_queue.length > 0
@command = @queue.pop
@command.process
end
end
When a connection is made, here is the output:
magicked$ ./server.rb
Waiting for socket accept
Socket accepted
Waiting for response
In the command queue
In the command queue ... (repeats)
Waiting for socket accept
In the command queue
In the command queue ... (repeats a lot)
Command received: EXEC 1 1 thisisacommand
Command initialized: EXEC 1 1 thisisacommand
Response complete
After this, it pauses again and waits for another connection/command. What I expected to see was the "In the command queue" continuing to repeat.
I probably haven't entirely wrapped my head around the way ruby threads work yet. I know the instance of the ruby interpreter has limitations when doing multiple threads. So is the loop reaching the @socket.accept again and it's blocking other instructions while waiting for another connection? Is my first thread completing and joining back up with the main thread, causing the second thread to do the same? Do I need to fork another ruby interpreter to handle one of these?
Finally, does anyone recommend a good resource that will help explain more advanced ruby threading? I've found plenty of simple instances, but obviously I still have a lot of confusion remaining.
Thanks for the help!