Reputation: 377
I am trying to run gnuplot from ruby (not using an external gem) and parsing its textual output also. I tried IO.popen
, PTY.spawn
and Open3.popen3
but whenever I try to get the output it just "hangs" -I guess waiting for more output to come. I feel like its somehow done using Thread.new
but I couldn't find the correct way to implement it.
Anyone know how it is done?
Upvotes: 3
Views: 1871
Reputation: 160553
The problem is that the sub-program is waiting for input that isn't being sent.
Typically, when we call a program that expects input on STDIN, we have to close STDIN, which then signals that program to begin processing. Look through the various Open3 methods and you'll see where stdin.close
occurs in many examples, but they don't explain why.
Open3 also includes capture2
and capture3
, which make it nice when trying to deal with a program that wants STDIN and you don't have anything to send to it. In both methods, STDIN is immediately closed, and the method returns the STDOUT, STDERR and exit status of the called program.
You need "expect" functionality. Ruby's Pty class includes an expect
method.
Creates and managed pseudo terminals (PTYs). See also en.wikipedia.org/wiki/Pseudo_terminal
It's not very well documented though, and doesn't offer a lot of functionality from what I've seen. An example of its use is available at "Using Ruby Expect Library to Reboot Ruckus Wireless Access Points via ssh".
Instead, you might want to look at RubyExpect which is better documented and appears to be current.
Upvotes: 1
Reputation: 1633
I guess this is what you want:
require 'pty'
require 'expect'
PTY.spawn('gnuplot') do |input, output, pid|
str = input.expect(/gnuplot>/)
puts str
output.puts "mlqksdf"
str = input.expect(/gnuplot>/)
puts str
output.puts "exit"
end
Upvotes: 3