kotp
9/19/2011 - 2:17 PM

irb3 - Run an IRB-esque prompt over multiple Ruby implementations at once using RVM

irb3 - Run an IRB-esque prompt over multiple Ruby implementations at once using RVM

#!/usr/bin/env ruby
# encoding: utf-8

# irb3 - Runs an IRB-esque prompt (but it's NOT really IRB!) over multiple
#        versions of Ruby at once (using RVM)
#        
#        By Peter Cooper, BSD licensed
#
#        Main dependency is term-ansicolor for each impl:
#          rvm exec gem install term-ansicolor
#
#        1. Type in expressions and press enter.
#        2. Leave space on the end of lines to enter more lines.
#        3. Add # all to run all versions, nothing for default
#        4. Add # version,version,version to run specific versions.
#        5. exit on its own to exit (or Ctrl+D)

require 'readline'
require 'term/ansicolor'
require 'tempfile'
include Term::ANSIColor

ALL_VERSIONS = %w{1.8.6 1.8.7 1.9.2 1.9.3}
DEFAULT_VERSIONS = %w{1.8.7 1.9.2}

loop do
  # Read lines
  lines = []
  begin
    line = Readline::readline('> ' + bold)
    print reset
    Readline::HISTORY << line
    line.chomp!
    lines << line
    exit if line =~ /^exit$/i
  end while line =~ /\s+$/
  
  # Determine versions to run
  versions = case line
  when /\# all$/
    ALL_VERSIONS.dup
  when /\#\s(.*)$/
    [*$1.strip.split(',').map(&:strip)]
  else
    DEFAULT_VERSIONS.dup
  end
  
  # Create code
  f = Tempfile.new('irb3')
  f.puts %{# encoding: utf-8
           require 'rubygems'
           require 'term/ansicolor'
           ARRAY = ['a', 'b', 'c']
           HASH = { :name => "Fred", :age => 40, :gender => :male }
           ARRAY2 = [1,2,3]
           STRING = "Hello"
           STRING2 = "çé"
           STRING3 = "ウabcé"
           o = begin
             Term::ANSIColor.green + eval(<<-'STUFFHERE'
               #{lines.join("\n")}
             STUFFHERE
             ).inspect + Term::ANSIColor.reset
           rescue Exception => e
             Term::ANSIColor.red + "!! \#{e.class}: \#{e.message}" + Term::ANSIColor.reset
           end
           print o}
  f.close
  
  versions.each do |version|  
    result = `rvm #{version} exec ruby #{f.path}`
    puts "  #{version} => #{result}"
  end

  puts
end