Я добавил $stdout.flush
в конец вашего скрипта, чтобы очистить вывод для каждой строки ввода:
loop do
line = gets.chomp
case line
when '1'
puts "i get number 1"
when '2'
puts "i get number 2"
else
puts "dont get any value"
break
end
$stdout.flush # flush output after each line of input
end
Чтобы получить доступ к скрипту в вашем контроллере, вы можете теперь сделать:
# allow writing to io by using r+ mode
# https://ruby-doc.org/core-2.6.5/IO.html#method-c-new-label-IO+Open+Mode
File.popen('ruby /path/to/script.rb', 'r+') do |io|
io.puts params[:my_options] # assuming params[:my_options] is "1"
io.gets #=> "i get number 1\n"
io.puts 2
io.gets #=> "i get number 2\n"
io.puts "foo bar" # falling in the else scenario breaks the loop, exiting the script
io.gets #=> "dont get any value\n"
io.puts 1
io.gets #=> nil
io.puts "foo bar"
io.gets #=> nil
end
Если вам нужно предоставить только один вход, вы можете вместо этого использовать backticks :
input = params[:my_options] # assuming params[:my_options] is "foo bar"
# escape special characters in double quoted context
# https://www.gnu.org/software/bash/manual/html_node/Double-Quotes.html
sanatized_input = input.gsub(/([$`\\"])/, '\\\\\1')
output = `echo "${sanatized_input}" | ruby /path/to/script.rb`
#=> "dont get any value\n"
Имейте в виду, что вы не справляетесь со сценарием, в котором вы предоставляете 1
или 2
и затем закройте вход. Когда это произойдет, следующий gets
вызов вернет nil
.
`echo 1 | ruby /path/to/script.rb`
# script.rb:2:in `block in <main>': undefined method `chomp' for nil:NilClass (NoMethodError)
# from script.rb:1:in `loop'
# from script.rb:1:in `<main>'
#=> "i get number 1\n"
Чтобы решить эту проблему, вы можете сделать что-то вроде:
loop do
line = gets or break # break the loop if gets returns nil
line.chomp!
# ...
end