lib/vagrant_snap.rb in vagrant-snap-0.09 vs lib/vagrant_snap.rb in vagrant-snap-0.10

- old
+ new

@@ -1,6 +1,8 @@ +require "virtualbox" require "colored" +require "pp" module Snap module VBox class SnapShot #{{{ class << self @@ -15,11 +17,11 @@ @@tree = nil end def parse_tree(vmname) init - vm = VirtualBox::VM.find( vmname ) + vm = ::VirtualBox::VM.find( vmname ) @@current = vm.current_snapshot return unless @@current @@tree = _parse(vm.root_snapshot) end @@ -66,10 +68,20 @@ else nil end end + def next_available_snapname + if lastname.nil? + "0" + else + n = lastname.succ + n = n.succ while VBox::SnapShot.include? n + n + end + end + def include?(name) return false unless tree tree.flatten.map(&:name).include? name end @@ -89,112 +101,158 @@ end end end #}}} end - class Command < Vagrant::Command::GroupBase - register "snap","Manages a snap" + class Snap < Vagrant::Command::Base + def help + puts <<-EOS +Usage: vagrant snap <subcommand> [options...] - no_tasks { - def env - @_env ||= Vagrant::Environment.new + subcommands are.. + vagrant snap list + vagrant snap back + vagrant snap go <snapshot> [boxname] + vagrant snap take [TARGET] [-n SNAP_NAME] [-d DESC]" + vagrant snap delete <snapshot> [boxname]" + + EOS + end + def execute# {{{ + @main_args, @sub_command, @sub_args = split_main_and_subcommand(@argv) + # p [@main_args, @sub_command, @sub_args] + + # sub_list = %w(list go back take delete test) + sub_list = %w(list go back take delete) + unless @sub_command + help + exit end + if sub_list.include? @sub_command + send(@sub_command) + else + ui.warn "unkown command '#{@sub_command}'" + help + exit + end + end# }}} - def with_target(target, &blk) - target_found = false - env.vms.each do |name, vm| - next if vm.vm.nil? # not yet created - vagvmname = vm.name - vmname = vm.vm.name + private + # def env + # @_env ||= Vagrant::Environment.new + # end - if target.nil? or target.to_sym == vagvmname - blk.call(vmname, vagvmname) - target_found = true - end + def ui# {{{ + @ui ||= ::Vagrant::UI::Colored.new("vagrant") + end# }}} + def safe_with_target_vms(target, &blk)# {{{ + with_target_vms(target) do |vm| + unless vm.created? + @logger.info("not created yet: #{vm.name}") + next end - warn "A VM by the name of `#{target}' was not found".red unless target_found + puts "[#{vm.name}]" + blk.call(vm) end - } + end# }}} + def target_vmname# {{{ + target = @sub_args.empty? ? nil : @sub_args.last.to_s + end# }}} + def exe(cmd)# {{{ + puts "# exe: #{cmd}" if @exe_verbose + system cmd + end# }}} - desc "list", "list snapshot" - def list(target=nil) - with_target(target) do |vmname, vagvmname| - puts "[#{vagvmname}]" - VBox::SnapShot.parse_tree( vmname ) - if VBox::SnapShot.tree - result = VBox::SnapShot.show - else - result = "no snapshot" - end - puts result + def list# {{{ + # options = {} + # opts = OptionParser.new { |opts| opts.banner = "vagrant snap list" } + # argv = parse_options(opts) + # # p argv + safe_with_target_vms(target_vmname) do |vm| + VBox::SnapShot.parse_tree( vm.uuid ) + puts VBox::SnapShot.tree ? VBox::SnapShot.show : "no snapshot" end - end - - desc "go SNAP_NAME", "go to specified snapshot" - def go(snapshot_name, target=nil) - with_target(target) do |vmname, vagvmname| - puts "[#{vagvmname}]" - VBox::SnapShot.parse_tree( vmname ) - if VBox::SnapShot.include?( snapshot_name ) - system "VBoxManage controlvm #{vmname} poweroff" - system "VBoxManage snapshot #{vmname} restore #{snapshot_name}" - system "VBoxManage startvm #{vmname} --type headless" + end# }}} + def go # {{{ + options = {} + opts = OptionParser.new do |opts| + opts.banner = "Usage: vagrant snapt go <snapshot> [boxname]" + end + snapshot, target = *@sub_args + unless snapshot + puts opts.help + return + end + safe_with_target_vms(target) do |vm| + VBox::SnapShot.parse_tree( vm.uuid ) + if VBox::SnapShot.include?( snapshot ) + exe "VBoxManage controlvm '#{vm.uuid}' poweroff" + exe "VBoxManage snapshot '#{vm.uuid}' restore '#{snapshot}'" + exe "VBoxManage startvm '#{vm.uuid}' --type headless" else - warn "#{snapshot_name} is not exist".red + ui.warn "'#{snapshot}' is not exist" end end - end - - desc "back", "back to current snapshot" - def back(target=nil) - with_target(target) do |vmname, vagvmname| - puts "[#{vagvmname}]" - system "VBoxManage controlvm #{vmname} poweroff" - system "VBoxManage snapshot #{vmname} restorecurrent" - system "VBoxManage startvm #{vmname} --type headless" + end# }}} + def back# {{{ + safe_with_target_vms(target_vmname) do |vm| + exe "VBoxManage controlvm '#{vm.uuid}' poweroff" + exe "VBoxManage snapshot '#{vm.uuid}' restorecurrent" + exe "VBoxManage startvm '#{vm.uuid}' --type headless" end - end + end# }}} + def take# {{{ + options = {} + opts = OptionParser.new do |opts| + opts.banner = "Usage: vagrant snap take [TARGET] [-n SNAP_NAME] [-d DESC]" + opts.on("-n", "--name STR", "Name of snapshot" ){ |v| options[:name] = v } + opts.on("-d", "--desc STR", "Description of snapshot"){ |v| options[:desc] = v } + end - desc "take [TARGET] [-n SNAP_NAME] [-d DESC]", "take snapshot" - method_option :desc, :type => :string, :aliases => "-d" - method_option :name, :type => :string, :aliases => "-n" - def take(target=nil) - with_target(target) do |vmname, vagvmname| - puts "[#{vagvmname}]" - VBox::SnapShot.parse_tree( vmname ) - if options.name - if VBox::SnapShot.include? options.name - warn "#{options.name} is already exist".red - next - else - new_name = options.name - end + begin + argv = parse_options(opts) + rescue OptionParser::MissingArgument + raise ::Vagrant::Errors::CLIInvalidOptions, :help => opts.help.chomp + end + return if !argv + @main_args, @sub_command, @sub_args = split_main_and_subcommand(argv) + # p @sub_args + # return + # snapshot, target = *@sub_args + safe_with_target_vms(target_vmname) do |vm| + VBox::SnapShot.parse_tree( vm.uuid ) + if options[:name] and VBox::SnapShot.include? options[:name] + ui.warn "'#{options[:name]}' is already exist" + next end - unless new_name - lastname = VBox::SnapShot.lastname - new_name = if lastname.nil? - "0" - else - n = lastname.succ - n = n.succ while VBox::SnapShot.include? n - n - end + snapshot = options[:name] ? options[:name] : VBox::SnapShot.next_available_snapname + cmd = "VBoxManage snapshot '#{vm.uuid}' take '#{snapshot}' --pause" + if options[:desc] + cmd << " --description '#{options[:desc]}'" end - desc = options.desc ? " --description '#{options.desc}'" : "" - system "VBoxManage snapshot '#{vmname}' take '#{new_name}' #{desc} --pause" + exe cmd end - end + end# }}} - desc "delete SNAP_NAME", "delete snapshot" - def delete(snapshot_name, target=nil) - with_target(target) do |vmname, vagvmname| - puts "[#{vagvmname}]" - VBox::SnapShot.parse_tree( vmname ) - if VBox::SnapShot.include?( snapshot_name ) - system "VBoxManage snapshot #{vmname} delete #{snapshot_name}" + def delete# {{{ + options = {} + opts = OptionParser.new do |opts| + opts.banner = "vagrant snap delete <snapshot> [boxname]" + end + snapshot, target = *@sub_args + unless snapshot + puts opts.help + return + end + snapshot, target = *@sub_args + safe_with_target_vms(target) do |vm| + VBox::SnapShot.parse_tree( vm.uuid ) + if VBox::SnapShot.include?( snapshot ) + exe "VBoxManage snapshot '#{vm.uuid}' delete '#{snapshot}'" else - warn "#{snapshot_name} is not exist".red + ui.warn "'#{snapshot}' is not exist" end end - end + end# }}} end end +Vagrant.commands.register(:snap) { ::Snap::Snap }