fission 0.3.0 → 0.4.0.beta.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (50) hide show
  1. data/.gitignore +1 -0
  2. data/CHANGELOG.md +3 -0
  3. data/README.md +1 -1
  4. data/lib/fission.rb +5 -6
  5. data/lib/fission/cli.rb +77 -7
  6. data/lib/fission/command.rb +43 -1
  7. data/lib/fission/command/clone.rb +19 -20
  8. data/lib/fission/command/delete.rb +29 -25
  9. data/lib/fission/command/snapshot_create.rb +11 -26
  10. data/lib/fission/command/snapshot_list.rb +13 -19
  11. data/lib/fission/command/snapshot_revert.rb +11 -26
  12. data/lib/fission/command/start.rb +11 -25
  13. data/lib/fission/command/status.rb +26 -10
  14. data/lib/fission/command/stop.rb +10 -21
  15. data/lib/fission/command/suspend.rb +21 -21
  16. data/lib/fission/command_helpers.rb +21 -0
  17. data/lib/fission/config.rb +35 -0
  18. data/lib/fission/fusion.rb +11 -3
  19. data/lib/fission/lease.rb +148 -0
  20. data/lib/fission/metadata.rb +55 -2
  21. data/lib/fission/response.rb +76 -0
  22. data/lib/fission/ui.rb +49 -0
  23. data/lib/fission/version.rb +1 -1
  24. data/lib/fission/vm.rb +653 -75
  25. data/spec/contexts/command.rb +12 -0
  26. data/spec/fission/cli_spec.rb +4 -11
  27. data/spec/fission/command/clone_spec.rb +45 -45
  28. data/spec/fission/command/delete_spec.rb +56 -43
  29. data/spec/fission/command/snapshot_create_spec.rb +29 -51
  30. data/spec/fission/command/snapshot_list_spec.rb +25 -26
  31. data/spec/fission/command/snapshot_revert_spec.rb +27 -53
  32. data/spec/fission/command/start_spec.rb +25 -69
  33. data/spec/fission/command/status_spec.rb +48 -13
  34. data/spec/fission/command/stop_spec.rb +25 -42
  35. data/spec/fission/command/suspend_spec.rb +54 -49
  36. data/spec/fission/command_helpers_spec.rb +30 -0
  37. data/spec/fission/command_spec.rb +19 -0
  38. data/spec/fission/config_spec.rb +24 -0
  39. data/spec/fission/fusion_spec.rb +6 -6
  40. data/spec/fission/lease_spec.rb +176 -0
  41. data/spec/fission/metadata_spec.rb +8 -8
  42. data/spec/fission/response_spec.rb +81 -0
  43. data/spec/fission/vm_spec.rb +869 -193
  44. data/spec/fission_spec.rb +0 -6
  45. data/spec/helpers/command_helpers.rb +12 -0
  46. data/spec/helpers/response_helpers.rb +21 -0
  47. data/spec/matchers/be_a_successful_response.rb +7 -0
  48. data/spec/matchers/be_an_unsuccessful_response.rb +10 -0
  49. data/spec/spec_helper.rb +7 -0
  50. metadata +24 -5
@@ -1,82 +1,87 @@
1
1
  require File.expand_path('../../../spec_helper.rb', __FILE__)
2
2
 
3
3
  describe Fission::Command::Suspend do
4
+ include_context 'command_setup'
5
+
4
6
  before do
5
- @vm_info = ['foo']
6
- @string_io = StringIO.new
7
- Fission.stub!(:ui).and_return(Fission::UI.new(@string_io))
7
+ @target_vm = ['foo']
8
+ Fission::VM.stub(:new).and_return(@vm_mock)
9
+
10
+ @suspend_response_mock = mock('suspend_response')
11
+
12
+ @vm_mock.stub(:name).and_return(@target_vm.first)
8
13
  end
9
14
 
10
15
  describe 'execute' do
11
- it "should output an error and the help when no VM argument is passed in" do
12
- Fission::Command::Suspend.should_receive(:help)
16
+ subject { Fission::Command::Suspend }
13
17
 
14
- lambda {
15
- command = Fission::Command::Suspend.new
16
- command.execute
17
- }.should raise_error SystemExit
18
+ it_should_not_accept_arguments_of [], 'suspend'
18
19
 
19
- @string_io.string.should match /Incorrect arguments for suspend command/
20
- end
20
+ it 'should suspend the vm' do
21
+ @suspend_response_mock.stub_as_successful
21
22
 
22
- it "should output an error and exit if it can't find the vm" do
23
- Fission::VM.should_receive(:exists?).with(@vm_info.first).and_return(false)
23
+ @vm_mock.should_receive(:suspend).and_return(@suspend_response_mock)
24
24
 
25
- lambda {
26
- command = Fission::Command::Suspend.new @vm_info
27
- command.execute
28
- }.should raise_error SystemExit
25
+ command = Fission::Command::Suspend.new @target_vm
26
+ command.execute
29
27
 
30
- @string_io.string.should match /Unable to find the VM #{@vm_info.first}/
28
+ @string_io.string.should match /Suspending '#{@target_vm.first}'/
29
+ @string_io.string.should match /VM '#{@target_vm.first}' suspended/
31
30
  end
32
31
 
32
+ it 'should output an error and exit if there was an error suspending the vm' do
33
+ @suspend_response_mock.stub_as_unsuccessful
33
34
 
34
- it "should output and exit if the vm is not running" do
35
- Fission::VM.should_receive(:exists?).with(@vm_info.first).and_return(true)
36
- Fission::VM.should_receive(:all_running).and_return([])
35
+ @vm_mock.should_receive(:suspend).and_return(@suspend_response_mock)
37
36
 
38
- lambda {
39
- command = Fission::Command::Suspend.new @vm_info
40
- command.execute
41
- }.should raise_error SystemExit
42
-
43
- @string_io.string.should match /VM '#{@vm_info.first}' is not running/
44
- end
45
-
46
- it 'should try to suspend the vm if it is running' do
47
- @vm_mock = mock('vm_mock')
48
- Fission::VM.should_receive(:exists?).with(@vm_info.first).and_return(true)
49
- Fission::VM.should_receive(:all_running).and_return([@vm_info.first])
50
- Fission::VM.should_receive(:new).with(@vm_info.first).and_return(@vm_mock)
51
- @vm_mock.should_receive(:suspend)
52
-
53
- command = Fission::Command::Suspend.new @vm_info
54
- command.execute
37
+ command = Fission::Command::Suspend.new @target_vm
38
+ lambda { command.execute }.should raise_error SystemExit
55
39
 
56
- @string_io.string.should match /Suspending '#{@vm_info.first}'/
40
+ @string_io.string.should match /Suspending '#{@target_vm.first}'/
41
+ @string_io.string.should match /There was an error suspending the VM.+it blew up.+/m
57
42
  end
58
43
 
59
44
  describe 'with --all' do
60
- it 'should suspend all running VMs' do
45
+ before do
61
46
  @vm_mock_1 = mock('vm_mock_1')
62
47
  @vm_mock_2 = mock('vm_mock_2')
63
48
 
64
- vm_items = {'vm_1' => @vm_mock_1,
65
- 'vm_2' => @vm_mock_2
49
+ @vm_mock_1.stub(:name).and_return('vm_1')
50
+ @vm_mock_2.stub(:name).and_return('vm_2')
51
+
52
+ @vm_items = {'vm_1' => @vm_mock_1,
53
+ 'vm_2' => @vm_mock_2
66
54
  }
55
+ end
56
+
57
+ it 'should output an error and exit if there was an error getting the list of running vms' do
58
+ @all_running_response_mock.stub_as_unsuccessful
59
+
60
+ Fission::VM.should_receive(:all_running).and_return(@all_running_response_mock)
61
+
62
+ command = Fission::Command::Suspend.new ['--all']
63
+ lambda { command.execute }.should raise_error SystemExit
64
+
65
+ @string_io.string.should match /There was an error getting the list of running VMs.+it blew up.+/m
66
+ end
67
67
 
68
- Fission::VM.should_receive(:all_running).and_return(vm_items.keys)
68
+ it 'should suspend all running VMs' do
69
+ @all_running_response_mock.stub_as_successful @vm_items.values
70
+ @suspend_response_mock.stub_as_successful
71
+
72
+ Fission::VM.should_receive(:all_running).and_return(@all_running_response_mock)
69
73
 
70
- vm_items.each_pair do |name, mock|
71
- Fission::VM.should_receive(:new).with(name).and_return(mock)
72
- mock.should_receive(:suspend)
74
+ @vm_items.each_pair do |name, mock|
75
+ mock.should_receive(:suspend).and_return(@suspend_response_mock)
73
76
  end
74
77
 
75
78
  command = Fission::Command::Suspend.new ['--all']
76
79
  command.execute
77
80
 
78
- @string_io.string.should match /Suspending 'vm_1'/
79
- @string_io.string.should match /Suspending 'vm_2'/
81
+ @vm_items.keys.each do |vm|
82
+ @string_io.string.should match /Suspending '#{vm}'/
83
+ @string_io.string.should match /VM '#{vm}' suspended/
84
+ end
80
85
  end
81
86
  end
82
87
 
@@ -86,7 +91,7 @@ describe Fission::Command::Suspend do
86
91
  it 'should output info for this command' do
87
92
  output = Fission::Command::Suspend.help
88
93
 
89
- output.should match /suspend \[vm \| --all\]/
94
+ output.should match /suspend \[vm_name \| --all\]/
90
95
  end
91
96
  end
92
97
  end
@@ -0,0 +1,30 @@
1
+ require File.expand_path('../../spec_helper.rb', __FILE__)
2
+
3
+ describe Fission::CommandHelpers do
4
+ include_context 'command_setup'
5
+
6
+ before do
7
+ @object = Object.new
8
+ @object.extend Fission::CommandHelpers
9
+ end
10
+
11
+ describe 'incorrect_arguments' do
12
+ before do
13
+ @object.class.should_receive(:help).and_return('foo help')
14
+ @object.stub(:output)
15
+ @object.stub(:output_and_exit)
16
+ end
17
+
18
+ it "should output the command's help text" do
19
+ @object.should_receive(:output).with("foo help\n")
20
+ @object.incorrect_arguments 'delete'
21
+ end
22
+
23
+ it 'should output that the argumets are incorrect and exit' do
24
+ @object.should_receive(:output_and_exit).
25
+ with('Incorrect arguments for delete command', 1)
26
+ @object.incorrect_arguments 'delete'
27
+ end
28
+ end
29
+
30
+ end
@@ -22,4 +22,23 @@ describe Fission::Command do
22
22
  end
23
23
  end
24
24
 
25
+ describe 'ui' do
26
+ it 'should load a ui object' do
27
+ Fission::Command.new.ui.should be_a Fission::UI
28
+ end
29
+
30
+ [:output, :output_and_exit, :output_printf].each do |item|
31
+ it "should delegate '#{item.to_s}' to the ui instance" do
32
+ @ui_mock = mock('ui')
33
+ @ui_mock.should_receive(item)
34
+
35
+ Fission::UI.stub!(:new).and_return(@ui_mock)
36
+
37
+ @cmd_instance = Fission::Command.new
38
+ @cmd_instance.send item, 'foo'
39
+ end
40
+ end
41
+
42
+ end
43
+
25
44
  end
@@ -42,6 +42,30 @@ describe Fission::Config do
42
42
  end
43
43
  end
44
44
 
45
+ it 'should use the fusion default lease file' do
46
+ @config = Fission::Config.new
47
+ @config.attributes['lease_file'].should == '/var/db/vmware/vmnet-dhcpd-vmnet8.leases'
48
+ end
49
+
50
+ end
51
+
52
+ describe '[]' do
53
+ before do
54
+ @config_items = { 'vmrun_bin' => '/foo/bar/vmrun',
55
+ 'vmrun_cmd' => '/foo/bar/vmrun -T fusion',
56
+ 'plist_file' => '/foo/bar/plist',
57
+ 'gui_bin' => '/foo/bar/gui',
58
+ 'vm_dir' => '/foo/bar/vms'}
59
+ @config = Fission::Config.new
60
+ @config.attributes = @config_items
61
+ end
62
+
63
+ it 'should return the value for specifed key' do
64
+ @config_items.each_pair do |k, v|
65
+ @config[k].should == v
66
+ end
67
+ end
68
+
45
69
  end
46
70
 
47
71
  end
@@ -1,22 +1,22 @@
1
1
  require File.expand_path('../../spec_helper.rb', __FILE__)
2
2
 
3
3
  describe Fission::Fusion do
4
- describe 'self.is_running?' do
4
+ describe 'self.running?' do
5
5
  before do
6
6
  @cmd = "ps -ef | grep -v grep | "
7
- @cmd << "grep -c #{Fission.config.attributes['gui_bin'].gsub(' ', '\ ')} 2>&1"
7
+ @cmd << "grep -c #{Fission.config['gui_bin'].gsub(' ', '\ ')} 2>&1"
8
8
  end
9
9
 
10
- it 'should return true if the fusion app is running' do
10
+ it 'should return a successful response and true if the fusion app is running' do
11
11
  Fission::Fusion.should_receive(:`).with(@cmd).
12
12
  and_return("1\n")
13
- Fission::Fusion.is_running?.should == true
13
+ Fission::Fusion.running?.should == true
14
14
  end
15
15
 
16
- it 'should return false if the fusion app is not running' do
16
+ it 'should return a successful response and false if the fusion app is not running' do
17
17
  Fission::Fusion.should_receive(:`).with(@cmd).
18
18
  and_return("0\n")
19
- Fission::Fusion.is_running?.should == false
19
+ Fission::Fusion.running?.should == false
20
20
  end
21
21
  end
22
22
  end
@@ -0,0 +1,176 @@
1
+ require File.expand_path('../../spec_helper.rb', __FILE__)
2
+
3
+ describe Fission::Lease do
4
+ before do
5
+ @lease_info = [ { :ip_address => '172.16.248.197',
6
+ :mac_address => '00:0c:29:2b:af:50',
7
+ :start => '2011/10/11 01:50:58',
8
+ :end => '2011/10/11 02:20:58' },
9
+ { :ip_address => '172.16.248.132',
10
+ :mac_address => '00:0c:29:10:23:57',
11
+ :start => '2010/07/12 21:31:28',
12
+ :end => '2010/07/12 22:01:28' },
13
+ { :ip_address => '172.16.248.130',
14
+ :mac_address => '00:0c:29:b3:63:d0',
15
+ :start => '2010/05/27 00:54:52',
16
+ :end => '2010/05/27 01:24:52' },
17
+ { :ip_address => '172.16.248.129',
18
+ :mac_address => '00:0c:29:0a:e9:b3',
19
+ :start => '2010/02/16 23:16:05',
20
+ :end => '2010/02/16 23:46:05' } ]
21
+
22
+ @lease_file_content = '# This is a comment
23
+ # And here is another
24
+ lease 172.16.248.197 {
25
+ starts 2 2011/10/11 01:50:58;
26
+ ends 2 2011/10/11 02:20:58;
27
+ hardware ethernet 00:0c:29:2b:af:50;
28
+ }
29
+ lease 172.16.248.132 {
30
+ starts 1 2010/07/12 21:31:28;
31
+ ends 1 2010/07/12 22:01:28;
32
+ hardware ethernet 00:0c:29:10:23:57;
33
+ }
34
+ lease 172.16.248.130 {
35
+ starts 4 2010/05/27 00:54:52;
36
+ ends 4 2010/05/27 01:24:52;
37
+ hardware ethernet 00:0c:29:b3:63:d0;
38
+ }
39
+ lease 172.16.248.129 {
40
+ starts 2 2010/02/16 23:16:05;
41
+ ends 2 2010/02/16 23:46:05;
42
+ hardware ethernet 00:0c:29:0a:e9:b3;
43
+ }'
44
+ end
45
+
46
+ describe 'new' do
47
+ { :ip_address => '127.0.0.1',
48
+ :mac_address => '00:00:00:00:00:00',
49
+ :start => '2004/07/25 17:18:00',
50
+ :end => '2004/07/25 18:18:00' }
51
+ it 'should set the ip address' do
52
+ lease = Fission::Lease.new :ip_address => '127.0.0.1'
53
+ lease.ip_address.should == '127.0.0.1'
54
+ end
55
+
56
+ it 'should set the mac address' do
57
+ lease = Fission::Lease.new :mac_address => '00:00:00:00:00:00'
58
+ lease.mac_address.should == '00:00:00:00:00:00'
59
+ end
60
+
61
+ it 'should set the lease start date/time' do
62
+ date_time = DateTime.parse('2000/01/01 17:00:00')
63
+ lease = Fission::Lease.new :start => date_time
64
+ lease.start.should == date_time
65
+ end
66
+
67
+ it 'should set the lease end date/time' do
68
+ date_time = DateTime.parse('2000/01/01 17:00:00')
69
+ lease = Fission::Lease.new :end => date_time
70
+ lease.end.should == date_time
71
+ end
72
+ end
73
+
74
+ describe 'expired?' do
75
+ it 'should return true if the lease is expired' do
76
+ lease = Fission::Lease.new :end => DateTime.now - 1
77
+ lease.expired?.should == true
78
+ end
79
+
80
+ it 'should return false if the lease has not expired' do
81
+ lease = Fission::Lease.new :end => DateTime.now + 1
82
+ lease.expired?.should == false
83
+ end
84
+ end
85
+
86
+ describe 'self.all' do
87
+ it 'should query the configured lease file' do
88
+ File.should_receive(:read).with(Fission.config['lease_file']).
89
+ and_return('')
90
+
91
+ Fission::Lease.all
92
+ end
93
+
94
+ it 'should return a successful response with the list of the found leases' do
95
+ File.should_receive(:read).with(Fission.config['lease_file']).
96
+ and_return(@lease_file_content)
97
+
98
+ example_leases = @lease_info.collect do |lease|
99
+ Fission::Lease.new :ip_address => lease[:ip_address],
100
+ :mac_address => lease[:mac_address],
101
+ :start => DateTime.parse(lease[:start]),
102
+ :end => DateTime.parse(lease[:end])
103
+
104
+ end
105
+
106
+ response = Fission::Lease.all
107
+ response.should be_a_successful_response
108
+
109
+ response.data.each do |lease|
110
+ example_lease = example_leases.select { |l| l.ip_address == lease.ip_address }
111
+
112
+ [:ip_address, :mac_address, :start, :end].each do |attrib|
113
+ lease.send(attrib).should == example_lease.first.send(attrib)
114
+ end
115
+ end
116
+
117
+ end
118
+
119
+ it 'should return a successful response with an empty list if there are no leases found' do
120
+ File.should_receive(:read).with(Fission.config['lease_file']).
121
+ and_return('')
122
+ response = Fission::Lease.all
123
+ response.should be_a_successful_response
124
+ response.data.should == []
125
+ end
126
+
127
+ it 'should return an unsuccessful response if the configured lease file does not exist' do
128
+ File.should_receive(:file?).with(Fission.config['lease_file']).
129
+ and_return(false)
130
+ response = Fission::Lease.all
131
+ error_string = "Unable to find the lease file '#{Fission.config['lease_file']}'"
132
+ response.should be_an_unsuccessful_response(error_string)
133
+ end
134
+
135
+ end
136
+
137
+ describe 'self.find_by_mac_address' do
138
+ describe 'when able to get all of the leases' do
139
+ before do
140
+ File.should_receive(:read).with(Fission.config['lease_file']).
141
+ and_return(@lease_file_content)
142
+ end
143
+
144
+ it 'should return a response with the lease associated with the provided mac address' do
145
+
146
+ response = Fission::Lease.find_by_mac_address '00:0c:29:10:23:57'
147
+
148
+ response.should be_a_successful_response
149
+
150
+ response.data.ip_address.should == '172.16.248.132'
151
+ response.data.mac_address.should == '00:0c:29:10:23:57'
152
+ response.data.start.should == DateTime.parse('2010/07/12 21:31:28')
153
+ response.data.end.should == DateTime.parse('2010/07/12 22:01:28')
154
+ end
155
+
156
+ it "should return a response with nil if the mac address can't be found" do
157
+ response = Fission::Lease.find_by_mac_address('00:11:22:33:44:55')
158
+
159
+ response.should be_a_successful_response
160
+ response.data.should be_nil
161
+ end
162
+ end
163
+
164
+ it 'should return an unsuccessful response if there was an error getting all of the leases' do
165
+ @all_response_mock = mock('all_response')
166
+ @all_response_mock.stub_as_unsuccessful
167
+
168
+ Fission::Lease.stub(:all).and_return(@all_response_mock)
169
+
170
+ response = Fission::Lease.find_by_mac_address('00:11:22:33:44:55')
171
+
172
+ response.should be_an_unsuccessful_response
173
+ end
174
+ end
175
+
176
+ end
@@ -3,7 +3,7 @@ require File.expand_path('../../spec_helper.rb', __FILE__)
3
3
  describe Fission::Metadata do
4
4
  before do
5
5
  @plist_mock = mock('plist_mock')
6
- @plist_file_path = Fission.config.attributes['plist_file']
6
+ @plist_file_path = Fission.config['plist_file']
7
7
  @metadata = Fission::Metadata.new
8
8
  end
9
9
 
@@ -28,19 +28,19 @@ describe Fission::Metadata do
28
28
  end
29
29
 
30
30
  it 'should remove the vm item from the list if the vm path is in the list' do
31
- @metadata.delete_vm_restart_document(Fission::VM.path('foo'))
31
+ @metadata.delete_vm_restart_document(Fission::VM.new('foo').path)
32
32
  @metadata.content.should == { 'PLRestartDocumentPaths' => ['/vm/bar.vmwarevm']}
33
33
  end
34
34
 
35
35
  it 'should not doing anything if the vm is not in the list' do
36
- @metadata.delete_vm_restart_document(Fission::VM.path('baz'))
36
+ @metadata.delete_vm_restart_document(Fission::VM.new('baz').path)
37
37
  @metadata.content.should == @data
38
38
  end
39
39
 
40
40
  it 'should not do anything if the restart document list does not exist' do
41
41
  other_data = { 'OtherConfigItem' => ['foo', 'bar']}
42
42
  @metadata.content = other_data
43
- @metadata.delete_vm_restart_document(Fission::VM.path('foo'))
43
+ @metadata.delete_vm_restart_document(Fission::VM.new('foo').path)
44
44
  @metadata.content.should == other_data
45
45
  end
46
46
  end
@@ -52,12 +52,12 @@ describe Fission::Metadata do
52
52
  end
53
53
 
54
54
  it 'should remove the vm item from the list' do
55
- @metadata.delete_vm_favorite_entry(Fission::VM.path('foo'))
55
+ @metadata.delete_vm_favorite_entry(Fission::VM.new('foo').path)
56
56
  @metadata.content.should == { 'VMFavoritesListDefaults2' => [] }
57
57
  end
58
58
 
59
59
  it 'should not do anything if the vm is not in the list' do
60
- @metadata.delete_vm_favorite_entry(Fission::VM.path('bar'))
60
+ @metadata.delete_vm_favorite_entry(Fission::VM.new('bar').path)
61
61
  @metadata.content.should == @data
62
62
  end
63
63
  end
@@ -73,13 +73,13 @@ describe Fission::Metadata do
73
73
  it 'should remove the vm from the restart document list' do
74
74
  @md_mock.should_receive(:delete_vm_restart_document).with('/vm/foo.vmwarevm')
75
75
  @md_mock.stub!(:delete_vm_favorite_entry)
76
- Fission::Metadata.delete_vm_info(Fission::VM.path('foo'))
76
+ Fission::Metadata.delete_vm_info(Fission::VM.new('foo').path)
77
77
  end
78
78
 
79
79
  it 'should remove the vm from the favorite list' do
80
80
  @md_mock.should_receive(:delete_vm_favorite_entry).with('/vm/foo.vmwarevm')
81
81
  @md_mock.stub!(:delete_vm_restart_document)
82
- Fission::Metadata.delete_vm_info(Fission::VM.path('foo'))
82
+ Fission::Metadata.delete_vm_info(Fission::VM.new('foo').path)
83
83
  end
84
84
  end
85
85