kitchen-openstack 2.1.1 → 2.2.0.pre.1

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 69c69a59c3e8c2bfdb001296bfe5949b6bf45430
4
- data.tar.gz: 2c6b438b1af153db872ddf311a56caa76bbcc1bf
3
+ metadata.gz: 059bf269f5416a2a5a5bcc11a3e68844b487c61b
4
+ data.tar.gz: 1c8d23e64ba66875ef55645883c8b08cb8771612
5
5
  SHA512:
6
- metadata.gz: 04ebc0f118339b453c235970fe51bb58ade74e93b3c83e8e0226efb360b56ac4d8c0ff68605d467934fd6eb7bd4b8589d70253b14db0a7bfeef3c965e52a5449
7
- data.tar.gz: ed824128dd046d02eb63579418022da643a965b4eccf7c95a8135f92cb5a823199627e760f1ea040195c46c1c5ba8c01df361bdf995a17633c8fd96c17adcea4
6
+ metadata.gz: 542449b370fe53182781a840bd1b3808e8dc3efd4d4ad9e65d0f360ed1fae79f7a01c73ed6d5459cc450f04245995701f9343a92a43a302c77b1af6320db8ad0
7
+ data.tar.gz: 6597a4224677f92de822959d5c1483bbf278d17c94c2216de93e74e06947a0342022b9eacc15ed460d2743312cf109ded22591a350581f82dae96e5237b4968e
data/CHANGELOG.md CHANGED
@@ -1,5 +1,11 @@
1
1
  # Change Log
2
2
 
3
+ [Full Changelog](https://github.com/test-kitchen/kitchen-openstack/compare/v2.1.1...HEAD)
4
+
5
+ **Merged pull requests:**
6
+
7
+ - Updated README with key\_name issue. [\#127](https://github.com/test-kitchen/kitchen-openstack/pull/127) ([jjasghar](https://github.com/jjasghar))
8
+ - Use OpenStack models for waiting for conditions [\#120](https://github.com/test-kitchen/kitchen-openstack/pull/120) ([carpnick](https://github.com/carpnick))
3
9
 
4
10
  ## [v2.1.1](https://github.com/test-kitchen/kitchen-openstack/tree/v2.1.1) (2015-11-03)
5
11
  [Full Changelog](https://github.com/test-kitchen/kitchen-openstack/compare/v2.1.0...v2.1.1)
@@ -10,6 +16,7 @@
10
16
 
11
17
  **Merged pull requests:**
12
18
 
19
+ - 2.1.1 [\#125](https://github.com/test-kitchen/kitchen-openstack/pull/125) ([jjasghar](https://github.com/jjasghar))
13
20
  - Ohai hint file is now created with the correct encoding on Windows [\#124](https://github.com/test-kitchen/kitchen-openstack/pull/124) ([stuartpreston](https://github.com/stuartpreston))
14
21
  - Added info about user\_data [\#121](https://github.com/test-kitchen/kitchen-openstack/pull/121) ([jjasghar](https://github.com/jjasghar))
15
22
 
@@ -400,6 +407,3 @@
400
407
  [Full Changelog](https://github.com/test-kitchen/kitchen-openstack/compare/v0.5.1...v0.5.2)
401
408
 
402
409
  ## [v0.5.1](https://github.com/test-kitchen/kitchen-openstack/tree/v0.5.1) (2011-04-05)
403
-
404
-
405
- \* *This Change Log was automatically generated by [github_changelog_generator](https://github.com/skywinder/Github-Changelog-Generator)*
data/README.md CHANGED
@@ -118,8 +118,15 @@ If a `key_name` is provided it will be used instead of any
118
118
  If a `key_name` is provided without any `private_key_path`, unexpected
119
119
  behavior may result if your local RSA/DSA private key doesn't match that
120
120
  OpenStack key. If you do key injection via `cloud-init` like this issue:
121
- [#77](https://github.com/test-kitchen/kitchen-openstack/issues/77) the best
122
- way is to make a "dummy-key."
121
+ [#77](https://github.com/test-kitchen/kitchen-openstack/issues/77). The
122
+ `key_name` should be a blank string if you need to skip it. Example:
123
+
124
+ ```yml
125
+ driver:
126
+ [-- snip --]
127
+ key_name: ""
128
+ user_data: cloud_init
129
+ ```
123
130
 
124
131
  ### username
125
132
 
@@ -154,6 +161,9 @@ Your OpenStack compute service name.
154
161
  Your OpenStack network name used to connect to, if you have only private network
155
162
  connections you want declare this.
156
163
 
164
+ ### glance\_cache\_wait\_timeout
165
+ When OpenStack downloads the image into cache, it takes extra time to provision. Timeout controls maximum amount of time to wait for machine to move from the Build/Spawn phase to Active.
166
+
157
167
  ### server\_wait
158
168
 
159
169
  `server_wait` is a workaround to deal with how some VMs with `cloud-init`.
@@ -253,6 +263,9 @@ The volume type, this is optional.
253
263
  This will delete the volume on the instance when `destroy` happens, if set to true.
254
264
  Otherwise set this to `false`.
255
265
 
266
+ #### creation\_timeout
267
+ Timeout to wait for volume to become available. If a large volume is provisioned, it might take time to provision it on the backend. Maximum amount of time to wait for volume to be created and be available.
268
+
256
269
  #### Example
257
270
 
258
271
  ```yaml
@@ -262,6 +275,7 @@ block_device_mappings:
262
275
  device_name: vda
263
276
  availability_zone: nova
264
277
  delete_on_termination: false
278
+ creation_timeout: 120
265
279
  ```
266
280
 
267
281
  ## Network and Communication Configuration
@@ -63,6 +63,7 @@ module Kitchen
63
63
  default_config :no_ssh_tcp_check, false
64
64
  default_config :no_ssh_tcp_check_sleep, 120
65
65
  default_config :winrm_wait, nil
66
+ default_config :glance_cache_wait_timeout, 600
66
67
  default_config :block_device_mapping, nil
67
68
 
68
69
  required_config :private_key_path
@@ -96,8 +97,14 @@ module Kitchen
96
97
  server = create_server
97
98
  state[:server_id] = server.id
98
99
  info "OpenStack instance with ID of <#{state[:server_id]}> is ready." # rubocop:disable Metrics/LineLength
100
+
99
101
  # this is due to the glance_caching issues. Annoying yes, but necessary.
100
- sleep 30
102
+ debug "Waiting for VM to be in ACTIVE state for a max time of:#{config[:glance_cache_wait_timeout]} seconds" # rubocop:disable Metrics/LineLength
103
+ server.wait_for(config[:glance_cache_wait_timeout]) do
104
+ sleep(1)
105
+ ready?
106
+ end
107
+
101
108
  if config[:floating_ip]
102
109
  attach_ip(server, config[:floating_ip])
103
110
  elsif config[:floating_ip_pool]
@@ -152,7 +159,7 @@ module Kitchen
152
159
  end
153
160
 
154
161
  def volume
155
- Volume.new
162
+ Volume.new(logger)
156
163
  end
157
164
 
158
165
  def get_bdm(config)
@@ -27,15 +27,14 @@ module Kitchen
27
27
  #
28
28
  # @author Liam Haworth <liam.haworth@bluereef.com.au>
29
29
  class Volume
30
- def volume(openstack_server)
31
- Fog::Volume.new(openstack_server)
30
+ @@default_creation_timeout = 60
31
+
32
+ def initialize(logger)
33
+ @logger = logger
32
34
  end
33
35
 
34
- def volume_ready?(vol_id, os)
35
- resp = volume(os).get_volume_details(vol_id)
36
- status = resp[:body]['volume']['status']
37
- fail "Failed to make volume <#{vol_id}>" if status == 'error'
38
- status == 'available'
36
+ def volume(openstack_server)
37
+ Fog::Volume.new(openstack_server)
39
38
  end
40
39
 
41
40
  def create_volume(config, os)
@@ -46,12 +45,31 @@ module Kitchen
46
45
  vanilla_options.select { |o| bdm[o] }.each do |key|
47
46
  opt[key] = bdm[key]
48
47
  end
48
+ @logger.info 'Creating Volume...'
49
49
  resp = volume(os).create_volume("#{config[:server_name]}-volume",
50
50
  "#{config[:server_name]} volume",
51
51
  bdm[:volume_size],
52
52
  opt)
53
53
  vol_id = resp[:body]['volume']['id']
54
- sleep(1) until volume_ready?(vol_id, os)
54
+
55
+ # Get Volume Model to make waiting for ready easy
56
+ vol_model = volume(os).volumes.first { |x| x.id == vol_id }
57
+
58
+ # Use default creation timeout or user supplied
59
+ creation_timeout = @@default_creation_timeout
60
+ if bdm.key?(:creation_timeout)
61
+ creation_timeout = bdm[:creation_timeout]
62
+ end
63
+
64
+ @logger.debug "Waiting for volume to be ready for #{creation_timeout} seconds" # rubocop:disable Metrics/LineLength
65
+ vol_model.wait_for(creation_timeout) do
66
+ sleep(1)
67
+ fail('Failed to make volume') if status.downcase == 'error'
68
+ ready?
69
+ end
70
+
71
+ @logger.debug 'Volume Ready'
72
+
55
73
  vol_id
56
74
  end
57
75
 
@@ -22,6 +22,6 @@ module Kitchen
22
22
  #
23
23
  # @author Jonathan Hartman <j@p4nt5.com>
24
24
  module Driver
25
- OPENSTACK_VERSION = '2.1.1'
25
+ OPENSTACK_VERSION = '2.2.0.pre.1'
26
26
  end
27
27
  end
@@ -20,10 +20,11 @@ describe Kitchen::Driver::Openstack::Volume do
20
20
  openstack_service_name: 'the_service'
21
21
  }
22
22
  end
23
-
23
+ let(:logger_io) { StringIO.new }
24
+ let(:logger) { Kitchen::Logger.new(logdev: logger_io) }
24
25
  describe '#volume' do
25
26
  let(:vol_driver) do
26
- described_class.new
27
+ described_class.new(logger)
27
28
  end
28
29
 
29
30
  it 'creates a new block device connection' do
@@ -31,38 +32,14 @@ describe Kitchen::Driver::Openstack::Volume do
31
32
  expect(vol_driver.send(:volume, os)).to eq(os)
32
33
  end
33
34
  end
34
-
35
- describe '#volume_ready?' do
36
- let(:volume_details) do
37
- {
38
- body: { 'volume' => { 'status' => 'available' } }
39
- }
40
- end
41
-
42
- let(:volume) do
43
- double(
44
- get_volume_details: volume_details
45
- )
46
- end
47
-
48
- let(:vol_driver) do
49
- d = described_class.new
50
- allow(d).to receive(:volume).and_return(volume)
51
- d
52
- end
53
-
54
- it 'checks if the volume is ready' do
55
- expect(vol_driver.send(:volume_ready?, '333', os)).to eq(true)
56
- end
57
- end
58
-
59
35
  describe '#create_volume' do
60
36
  let(:config) do
61
37
  {
62
38
  server_name: 'applejack',
63
39
  block_device_mapping: {
64
40
  snapshot_id: '444',
65
- volume_size: '5'
41
+ volume_size: '5',
42
+ creation_timeout: '30'
66
43
  }
67
44
  }
68
45
  end
@@ -73,20 +50,47 @@ describe Kitchen::Driver::Openstack::Volume do
73
50
  }
74
51
  end
75
52
 
53
+ let(:volume_model) do
54
+ {
55
+ id: '555',
56
+ status: 'ACTIVE'
57
+ # wait_for: true
58
+ # ready?: true
59
+ }
60
+ end
61
+
76
62
  let(:volume) do
77
63
  double(
78
- create_volume: create_volume
64
+ create_volume: create_volume,
65
+ volumes: [volume_model]
79
66
  )
80
67
  end
81
68
 
69
+ let(:wait_for) do
70
+ {
71
+ ready?: true,
72
+ status: 'ACTIVE'
73
+ }
74
+ end
75
+
82
76
  let(:vol_driver) do
83
- d = described_class.new
77
+ d = described_class.new(logger)
84
78
  allow(d).to receive(:volume).and_return(volume)
85
- allow(d).to receive(:volume_ready?).and_return(true)
79
+ allow(d).to receive(:volume_model).and_return(true)
86
80
  d
87
81
  end
88
82
 
89
83
  it 'creates a volume' do
84
+ # This seems like a hack
85
+ # how would we do this on the volume_model instead?
86
+ # This makes rspec work
87
+ # but the vol_driver doesnt have these methods properties?
88
+ allow(vol_driver).to receive(:status).and_return('ACTIVE')
89
+ allow(vol_driver).to receive(:ready?).and_return(true)
90
+ allow(volume_model).to receive(:wait_for)
91
+ .with(an_instance_of(String)).and_yield
92
+
93
+ # allow(vol_driver).a
90
94
  expect(vol_driver.send(:create_volume, config, os)).to eq('555')
91
95
  end
92
96
  end
@@ -106,7 +110,7 @@ describe Kitchen::Driver::Openstack::Volume do
106
110
  end
107
111
 
108
112
  let(:vol_driver) do
109
- d = described_class.new
113
+ d = described_class.new(logger)
110
114
  allow(d).to receive(:create_volume).and_return('555')
111
115
  d
112
116
  end
@@ -12,6 +12,8 @@ require 'kitchen/provisioner/dummy'
12
12
  require 'kitchen/transport/dummy'
13
13
  require 'kitchen/verifier/dummy'
14
14
  require 'ohai'
15
+ require 'excon'
16
+ require 'fog'
15
17
 
16
18
  describe Kitchen::Driver::Openstack do
17
19
  let(:logged_output) { StringIO.new }
@@ -201,22 +203,53 @@ describe Kitchen::Driver::Openstack do
201
203
  d
202
204
  end
203
205
 
206
+ context 'when a server is already created' do
207
+ it 'does not create a new instance' do
208
+ state[:server_id] = '1'
209
+ expect(driver).not_to receive(:create_server)
210
+ driver.create(state)
211
+ end
212
+ end
213
+
204
214
  context 'required options provided' do
205
215
  let(:config) do
206
216
  {
207
217
  openstack_username: 'hello',
208
218
  openstack_api_key: 'world',
209
219
  openstack_auth_url: 'http:',
210
- openstack_tenant: 'www'
220
+ openstack_tenant: 'www',
221
+ glance_cache_wait_timeout: 600,
222
+ disable_ssl_validation: false
211
223
  }
212
224
  end
213
- end
225
+ let(:server) do
226
+ double(id: 'test123', wait_for: true, public_ip_addresses: %w(1.2.3.4))
227
+ end
214
228
 
215
- context 'when a server is already created' do
216
- it 'does not create a new instance' do
217
- state[:server_id] = '123'
218
- expect(driver).not_to receive(:create_server)
219
- driver.create(state)
229
+ let(:driver) do
230
+ d = described_class.new(config)
231
+ allow(d).to receive(:config_server_name).and_return('a_monkey!')
232
+ allow(d).to receive(:create_server).and_return(server)
233
+ allow(server).to receive(:id).and_return('test123')
234
+
235
+ # Inside the yield block we are calling ready? So we fake it here
236
+ allow(d).to receive(:ready?).and_return(true)
237
+ allow(server).to receive(:wait_for)
238
+ .with(an_instance_of(Fixnum)).and_yield
239
+
240
+ allow(d).to receive(:get_ip).and_return('1.2.3.4')
241
+ allow(d).to receive(:bourne_shell?).and_return(false)
242
+ d
243
+ end
244
+
245
+ it 'returns nil, but modifies the state' do
246
+ expect(driver.send(:create, state)).to eq(nil)
247
+ expect(state[:server_id]).to eq('test123')
248
+ end
249
+
250
+ it 'throws an Action error when trying to create_server' do
251
+ allow(driver).to receive(:create_server).and_raise(Fog::Errors::Error)
252
+ expect { driver.send(:create, state) }.to raise_error(Kitchen::ActionFailed) # rubocop:disable Metrics/LineLength
220
253
  end
221
254
  end
222
255
  end
@@ -1081,6 +1114,38 @@ describe Kitchen::Driver::Openstack do
1081
1114
  end
1082
1115
  end
1083
1116
 
1117
+ describe '#setup_ssh' do
1118
+ let(:config) { { public_key_path: '/pub_key' } }
1119
+ let(:config) do
1120
+ {
1121
+ public_key_path: '/pub_key',
1122
+ key_name: 'OpenStackKey'
1123
+ }
1124
+ end
1125
+
1126
+ let(:server) { double(password: 'aloha') }
1127
+ let(:state) { { hostname: 'host' } }
1128
+ let(:read) { double(read: 'a_key') }
1129
+ let(:ssh) { double(run: true) }
1130
+
1131
+ before(:each) do
1132
+ allow(driver).to receive(:open).with(config[:public_key_path])
1133
+ .and_return(read)
1134
+ end
1135
+
1136
+ context 'sets the ssh_key state' do
1137
+ before do
1138
+ allow(driver).to receive(:bourne_shell?).and_return(false)
1139
+ allow(driver).to receive(:do_ssh_setup).and_return(nil)
1140
+ end
1141
+
1142
+ it 'does not execute the ssh setup' do
1143
+ expect(driver).not_to receive(:do_ssh_setup)
1144
+ driver.send(:setup_ssh, server, state)
1145
+ end
1146
+ end
1147
+ end
1148
+
1084
1149
  describe '#do_ssh_setup' do
1085
1150
  let(:config) { { public_key_path: '/pub_key' } }
1086
1151
  let(:server) { double(password: 'aloha') }
@@ -1136,6 +1201,12 @@ describe Kitchen::Driver::Openstack do
1136
1201
  it 'opens an SSH session to the server' do
1137
1202
  driver.send(:add_ohai_hint, state)
1138
1203
  end
1204
+
1205
+ it 'opens an Winrm session to the server' do
1206
+ allow(driver).to receive(:bourne_shell?).and_return(false)
1207
+ allow(driver).to receive(:windows_os?).and_return(true)
1208
+ driver.send(:add_ohai_hint, state)
1209
+ end
1139
1210
  end
1140
1211
 
1141
1212
  describe '#disable_ssl_validation' do
@@ -1143,4 +1214,84 @@ describe Kitchen::Driver::Openstack do
1143
1214
  expect(driver.send(:disable_ssl_validation)).to eq(false)
1144
1215
  end
1145
1216
  end
1217
+
1218
+ describe '#countdown' do
1219
+ it 'counts down to future time with 0 seconds with almost no time' do
1220
+ current = Time.now
1221
+ driver.send(:countdown, 0)
1222
+ after = Time.now
1223
+ expect(after - current).to be >= 0
1224
+ expect(after - current).to be < 10
1225
+ end
1226
+
1227
+ it 'counts down to future time with 1 seconds with at least 9 seconds' do
1228
+ current = Time.now
1229
+ driver.send(:countdown, 1)
1230
+ after = Time.now
1231
+ expect(after - current).to be >= 9
1232
+ end
1233
+ end
1234
+
1235
+ describe '#wait_for_server' do
1236
+ let(:config) { { server_wait: 0 } }
1237
+ let(:state) { { hostname: 'host' } }
1238
+
1239
+ it 'waits for connection to be available' do
1240
+ expect(driver.send(:wait_for_server, state)).to be(nil)
1241
+ end
1242
+
1243
+ it 'Fails when calling transport but still destroys the created system' do
1244
+ allow(instance.transport).to receive(:connection).and_raise(ArgumentError)
1245
+ expect(driver).to receive(:destroy)
1246
+
1247
+ expect { driver.send(:wait_for_server, state) }
1248
+ .to raise_error(ArgumentError)
1249
+ end
1250
+ end
1251
+
1252
+ describe '#get_bdm' do
1253
+ let(:logger) { Logger.new(logged_output) }
1254
+ let(:config) do
1255
+ {
1256
+ openstack_username: 'a',
1257
+ openstack_api_key: 'b',
1258
+ openstack_auth_url: 'http://',
1259
+ openstack_tenant: 'me',
1260
+ openstack_region: 'ORD',
1261
+ openstack_service_name: 'stack',
1262
+ image_ref: '22',
1263
+ flavor_ref: '33',
1264
+ public_key_path: '/tmp',
1265
+ username: 'admin',
1266
+ port: '2222',
1267
+ server_name: 'puppy',
1268
+ server_name_prefix: 'parsnip',
1269
+ private_key_path: '/path/to/id_rsa',
1270
+ floating_ip_pool: 'swimmers',
1271
+ floating_ip: '11111',
1272
+ network_ref: '0xCAFFE',
1273
+ block_device_mapping: {
1274
+ volume_id: '55',
1275
+ volume_size: '5',
1276
+ device_name: 'vda',
1277
+ delete_on_termination: true
1278
+ }
1279
+ }
1280
+ end
1281
+ it 'returns just the BDM config' do
1282
+ expect(driver.send(:get_bdm, config)).to eq(config[:block_device_mapping])
1283
+ end
1284
+ end
1285
+
1286
+ describe '#config_server_name' do
1287
+ let(:config) do
1288
+ {
1289
+ server_name_prefix: 'parsnip'
1290
+ }
1291
+ end
1292
+
1293
+ it 'returns random string prefixed by servername_prefix attribute' do
1294
+ expect(driver.send(:config_server_name)).to include('parsnip')
1295
+ end
1296
+ end
1146
1297
  end
data/spec/spec_helper.rb CHANGED
@@ -10,7 +10,8 @@ SimpleCov.formatter = SimpleCov::Formatter::MultiFormatter[
10
10
  SimpleCov::Formatter::HTMLFormatter,
11
11
  SimpleCov::Formatter::Console
12
12
  ]
13
- SimpleCov.minimum_coverage 90
13
+ SimpleCov.minimum_coverage 95
14
14
  SimpleCov.start do
15
15
  add_filter '/vendor/'
16
+ add_filter '/spec/'
16
17
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: kitchen-openstack
3
3
  version: !ruby/object:Gem::Version
4
- version: 2.1.1
4
+ version: 2.2.0.pre.1
5
5
  platform: ruby
6
6
  authors:
7
7
  - Jonathan Hartman
@@ -9,7 +9,7 @@ authors:
9
9
  autorequire:
10
10
  bindir: bin
11
11
  cert_chain: []
12
- date: 2015-11-03 00:00:00.000000000 Z
12
+ date: 2015-11-23 00:00:00.000000000 Z
13
13
  dependencies:
14
14
  - !ruby/object:Gem::Dependency
15
15
  name: test-kitchen
@@ -237,9 +237,9 @@ required_ruby_version: !ruby/object:Gem::Requirement
237
237
  version: 2.0.0
238
238
  required_rubygems_version: !ruby/object:Gem::Requirement
239
239
  requirements:
240
- - - ">="
240
+ - - ">"
241
241
  - !ruby/object:Gem::Version
242
- version: '0'
242
+ version: 1.3.1
243
243
  requirements: []
244
244
  rubyforge_project:
245
245
  rubygems_version: 2.2.2