From 29458061df6b4a349b701bd0860de7959bed54d0 Mon Sep 17 00:00:00 2001 From: Mitchell Hashimoto Date: Mon, 5 Jul 2010 20:09:39 +0200 Subject: [PATCH] Added insert, swap, and delete helpers to Vagrant::Action::Builder --- lib/vagrant/action/builder.rb | 46 +++++++++++++++++ test/vagrant/action/builder_test.rb | 80 +++++++++++++++++++++++++++++ 2 files changed, 126 insertions(+) diff --git a/lib/vagrant/action/builder.rb b/lib/vagrant/action/builder.rb index c828c1eb6..54f77a3e7 100644 --- a/lib/vagrant/action/builder.rb +++ b/lib/vagrant/action/builder.rb @@ -45,6 +45,52 @@ module Vagrant end end + # Inserts a middleware at the given index or directly before the + # given middleware object. + def insert(index, middleware, *args, &block) + index = self.index(index) unless index.is_a?(Integer) + stack.insert(index, [middleware, args, block]) + end + + alias_method :insert_before, :insert + + # Inserts a middleware after the given index or middleware object. + def insert_after(index, middleware, *args, &block) + index = self.index(index) unless index.is_a?(Integer) + raise "no such middleware to insert after: #{index.inspect}" unless index + insert(index + 1, middleware, *args, &block) + end + + # Swaps out the given middlware object or index with the new + # middleware. + def swap(index, middleware, *args, &block) + if index.is_a?(Integer) + delete(index) + insert(index, middleware, *args, &block) + else + insert_before(index, middleware, *args, &block) + delete(index) + end + end + + # Deletes the given middleware object or index + def delete(index) + index = self.index(index) unless index.is_a?(Integer) + stack.delete_at(index) + end + + # Returns the numeric index for the given middleware object. + # + # @param [Object] object The item to find the index for + # @return [Integer] + def index(object) + stack.each_with_index do |item, i| + return i if item[0] == object + end + + nil + end + # Converts the builder stack to a runnable action sequence. # # @param [Vagrant::Action::Environment] env The action environment diff --git a/test/vagrant/action/builder_test.rb b/test/vagrant/action/builder_test.rb index 2b8aa372f..5f71e7aac 100644 --- a/test/vagrant/action/builder_test.rb +++ b/test/vagrant/action/builder_test.rb @@ -46,6 +46,86 @@ class ActionBuilderTest < Test::Unit::TestCase end end + context "inserting" do + setup do + @instance.use "1" + @instance.use "2" + end + + should "insert at the proper numeric index" do + @instance.insert(1, "3") + assert_equal "3", @instance.stack[1].first + end + + should "insert next to the proper object if given" do + @instance.insert("2", "3") + assert_equal "3", @instance.stack[1].first + end + + should "be able to call insert_before as well" do + @instance.insert_before("1", "0") + assert_equal "0", @instance.stack.first.first + end + + should "be able to insert_after" do + @instance.insert_after("1", "0") + assert_equal "0", @instance.stack[1].first + end + + should "be able to insert_after using numeric index" do + @instance.insert_after(1, "0") + assert_equal "0", @instance.stack[2].first + end + + should "raise an exception if invalid index" do + assert_raises(RuntimeError) { + @instance.insert_after("15", "0") + } + end + end + + context "swapping" do + setup do + @instance.use "1" + @instance.use "2" + end + + should "be able to swap using the object" do + @instance.swap "1", "3" + assert_equal "3", @instance.stack.first.first + end + + should "be able to swap using the index" do + @instance.swap 0, "3" + assert_equal "3", @instance.stack.first.first + end + end + + context "deleting" do + setup do + @instance.use "1" + end + + should "delete the proper object" do + @instance.delete("1") + assert @instance.stack.empty? + end + + should "delete by index if given" do + @instance.delete(0) + assert @instance.stack.empty? + end + end + + context "getting an index of an object" do + should "return the proper index if it exists" do + @instance.use 1 + @instance.use 2 + @instance.use 3 + assert_equal 1, @instance.index(2) + end + end + context "converting to an app" do should "preprend error halt to the chain" do result = mock("result")