examples/jexec2.rb
author Mahlon E. Smith <mahlon@martini.nu>
Tue, 03 Mar 2009 22:23:45 +0000
changeset 7 4460fc10c6a3
permissions -rwxr-xr-x
* Now with 87% more hot jail action! * Predeclared all C methods in jail.h, so they could be arranged in logical order in jail.c * Fixed the extconf namespace. * Added rdoc. * Added usage examples, demonstrating jls, jexec, and jail ruby equivalents. * Re-added the "attach and execute within a block" code. * Added Enumerable and Comparable support. * Return 'path' as a Pathname object. TODO: * Create the actual 'jParallel' shell binary, now that we have a good backend framework. * Tests? How? * Add support for recently committed (will be part of 7.2-RELEASE) multiple IPs per jail, and jail labels.

#!/usr/bin/env ruby
#
# A 'smarter' jexec in ruby.
#
# Run a command in multiple jails in parallel.
# Jails can be selected via host, ip, or jid.
#
#   "Run 'ls' in all jails that match the hostname 'trac':
#       ./jexec2.rb trac ls
#

BEGIN {
        require 'pathname'
        basedir = Pathname.new( __FILE__ ).dirname.parent

        $LOAD_PATH.unshift basedir + "ext" unless 
                $LOAD_PATH.include? basedir + "ext"
}

require 'jail'

jarg = ARGV.shift
args = ARGV

jails = BSD::Jail.find_all do |j|
    j.jid     == jarg.to_i ||
    j.ip.to_s == jarg      ||
    j.host    =~ /#{jarg}/
end or raise "Unable to find jails that match '#{jarg}'."


jails.each do |j|
    $deferr.puts "Parent #{Process.pid} about to attach to #{j.host} in a block!"
    childpid = j.attach do
        $deferr.puts "Child #{Process.pid} exec()ing:", "  " + args.join(" ")
        exec( *args )
    end

    $deferr.puts "Parent: waiting on imprisoned child #{childpid}"
    Process.waitpid( childpid )
    $deferr.puts "Child exited with exit code: %d" % [ $?.exitstatus ]
end