vmpooler 3.3.0 → 3.5.0

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
  SHA256:
3
- metadata.gz: b586b8ee56526b89f47621d090f932159c46df74c6935002e8a71c18a02503fb
4
- data.tar.gz: 51e4f7cf4dd4a5daa3130ab1bb60b08b4347196e1ba1c39f94a820d7356f2937
3
+ metadata.gz: 421d86151ba2c7a9bcc2310e3596b43f27a0280df1b7cb0c042dd12a63c80086
4
+ data.tar.gz: 7f8e2dea7fc3f4089995fc65022e98e48771f5a40cbbd30b51ddf162fad7b3f7
5
5
  SHA512:
6
- metadata.gz: 39ba39f114252e74a08a6c3dbebd773cb2dda74adfc33216b7774dbf8fb83109f2a61076a3435cab54f8dc39adcdef60ee1cac44f24b3f3f441c7ceaf389e813
7
- data.tar.gz: e295be65e92e61fad459d32d1a6171396b0599795355b99821d7bc8272ecbe19cfee78dd735c88e49653d5156afb7e529f12935d484fc2b1c479e5eed4be69e1
6
+ metadata.gz: 4722f36453f515e66cf69d2c9c19cd472dd289e012514b2823e6ccf2febbdc525d78969e4a24777779b2fd9dbf5c0f8137421e6fe0bdf95f726effead80cd114
7
+ data.tar.gz: 979d40b555d547d6ebec64efeb57af5cdb68eb90fbc6f759cf6a1bbfef074e66404b9e238ad410bd938cef611ae006e430aad86c754a50e3901d9c659081c733
@@ -68,7 +68,7 @@ module Vmpooler
68
68
  end
69
69
  end
70
70
 
71
- def authenticate_ldap(port, host, encryption_hash, user_object, base, username_str, password_str)
71
+ def authenticate_ldap(port, host, encryption_hash, user_object, base, username_str, password_str, service_account_hash = nil)
72
72
  tracer.in_span(
73
73
  "Vmpooler::API::Helpers.#{__method__}",
74
74
  attributes: {
@@ -79,6 +79,14 @@ module Vmpooler
79
79
  },
80
80
  kind: :client
81
81
  ) do
82
+ if service_account_hash
83
+ username = service_account_hash[:user_dn]
84
+ password = service_account_hash[:password]
85
+ else
86
+ username = "#{user_object}=#{username_str},#{base}"
87
+ password = password_str
88
+ end
89
+
82
90
  ldap = Net::LDAP.new(
83
91
  :host => host,
84
92
  :port => port,
@@ -86,12 +94,22 @@ module Vmpooler
86
94
  :base => base,
87
95
  :auth => {
88
96
  :method => :simple,
89
- :username => "#{user_object}=#{username_str},#{base}",
90
- :password => password_str
97
+ :username => username,
98
+ :password => password
91
99
  }
92
100
  )
93
101
 
94
- return true if ldap.bind
102
+ if service_account_hash
103
+ return true if ldap.bind_as(
104
+ :base => base,
105
+ :filter => "(#{user_object}=#{username_str})",
106
+ :password => password_str
107
+ )
108
+ elsif ldap.bind
109
+ return true
110
+ else
111
+ return false
112
+ end
95
113
 
96
114
  return false
97
115
  end
@@ -116,6 +134,7 @@ module Vmpooler
116
134
  :method => :start_tls,
117
135
  :tls_options => { :ssl_version => 'TLSv1' }
118
136
  }
137
+ service_account_hash = auth[:ldap]['service_account_hash']
119
138
 
120
139
  unless ldap_base.is_a? Array
121
140
  ldap_base = ldap_base.split
@@ -134,7 +153,8 @@ module Vmpooler
134
153
  search_user_obj,
135
154
  search_base,
136
155
  username_str,
137
- password_str
156
+ password_str,
157
+ service_account_hash
138
158
  )
139
159
  return true if result
140
160
  end
@@ -551,18 +571,6 @@ module Vmpooler
551
571
  end
552
572
  end
553
573
  end
554
-
555
- def vm_ready?(vm_name, domain = nil)
556
- tracer.in_span("Vmpooler::API::Helpers.#{__method__}") do
557
- begin
558
- open_socket(vm_name, domain)
559
- rescue StandardError => _e
560
- return false
561
- end
562
-
563
- true
564
- end
565
- end
566
574
  end
567
575
  end
568
576
  end
@@ -82,31 +82,31 @@ module Vmpooler
82
82
  end
83
83
 
84
84
  # Check the state of a VM
85
- def check_pending_vm(vm, pool, timeout, provider)
85
+ def check_pending_vm(vm, pool, timeout, timeout_notification, provider)
86
86
  Thread.new do
87
87
  begin
88
- _check_pending_vm(vm, pool, timeout, provider)
88
+ _check_pending_vm(vm, pool, timeout, timeout_notification, provider)
89
89
  rescue StandardError => e
90
90
  $logger.log('s', "[!] [#{pool}] '#{vm}' #{timeout} #{provider} errored while checking a pending vm : #{e}")
91
91
  @redis.with_metrics do |redis|
92
- fail_pending_vm(vm, pool, timeout, redis)
92
+ fail_pending_vm(vm, pool, timeout, timeout_notification, redis)
93
93
  end
94
94
  raise
95
95
  end
96
96
  end
97
97
  end
98
98
 
99
- def _check_pending_vm(vm, pool, timeout, provider)
99
+ def _check_pending_vm(vm, pool, timeout, timeout_notification, provider)
100
100
  mutex = vm_mutex(vm)
101
101
  return if mutex.locked?
102
102
 
103
103
  mutex.synchronize do
104
104
  @redis.with_metrics do |redis|
105
105
  request_id = redis.hget("vmpooler__vm__#{vm}", 'request_id')
106
- if provider.vm_ready?(pool, vm)
106
+ if provider.vm_ready?(pool, vm, redis)
107
107
  move_pending_vm_to_ready(vm, pool, redis, request_id)
108
108
  else
109
- fail_pending_vm(vm, pool, timeout, redis)
109
+ fail_pending_vm(vm, pool, timeout, timeout_notification, redis)
110
110
  end
111
111
  end
112
112
  end
@@ -122,34 +122,53 @@ module Vmpooler
122
122
  $logger.log('d', "[!] [#{pool}] '#{vm}' no longer exists. Removing from pending.")
123
123
  end
124
124
 
125
- def fail_pending_vm(vm, pool, timeout, redis, exists: true)
125
+ def fail_pending_vm(vm, pool, timeout, timeout_notification, redis, exists: true)
126
126
  clone_stamp = redis.hget("vmpooler__vm__#{vm}", 'clone')
127
-
128
127
  time_since_clone = (Time.now - Time.parse(clone_stamp)) / 60
129
- if time_since_clone > timeout
130
- if exists
131
- request_id = redis.hget("vmpooler__vm__#{vm}", 'request_id')
132
- pool_alias = redis.hget("vmpooler__vm__#{vm}", 'pool_alias') if request_id
133
- redis.smove("vmpooler__pending__#{pool}", "vmpooler__completed__#{pool}", vm)
134
- if request_id
135
- ondemandrequest_hash = redis.hgetall("vmpooler__odrequest__#{request_id}")
136
- if ondemandrequest_hash && ondemandrequest_hash['status'] != 'failed' && ondemandrequest_hash['status'] != 'deleted'
137
- # will retry a VM that did not come up as vm_ready? only if it has not been market failed or deleted
138
- redis.zadd('vmpooler__odcreate__task', 1, "#{pool_alias}:#{pool}:1:#{request_id}")
139
- end
140
- end
141
- $metrics.increment("errors.markedasfailed.#{pool}")
142
- $logger.log('d', "[!] [#{pool}] '#{vm}' marked as 'failed' after #{timeout} minutes")
143
- else
128
+
129
+ already_timed_out = time_since_clone > timeout
130
+ timing_out_soon = time_since_clone > timeout_notification && !redis.hget("vmpooler__vm__#{vm}", 'timeout_notification')
131
+
132
+ if already_timed_out
133
+ unless exists
144
134
  remove_nonexistent_vm(vm, pool, redis)
135
+ return true
145
136
  end
137
+ open_socket_error = handle_timed_out_vm(vm, pool, redis)
146
138
  end
139
+
140
+ redis.hset("vmpooler__vm__#{vm}", 'timeout_notification', 1) if timing_out_soon
141
+
142
+ nonexist_warning = if already_timed_out
143
+ "[!] [#{pool}] '#{vm}' marked as 'failed' after #{timeout} minutes with error: #{open_socket_error}"
144
+ elsif timing_out_soon
145
+ "[!] [#{pool}] '#{vm}' no longer exists when attempting to send notification of impending failure"
146
+ else
147
+ "[!] [#{pool}] '#{vm}' This error is wholly unexpected"
148
+ end
149
+ $logger.log('d', nonexist_warning)
147
150
  true
148
151
  rescue StandardError => e
149
152
  $logger.log('d', "Fail pending VM failed with an error: #{e}")
150
153
  false
151
154
  end
152
155
 
156
+ def handle_timed_out_vm(vm, pool, redis)
157
+ request_id = redis.hget("vmpooler__vm__#{vm}", 'request_id')
158
+ pool_alias = redis.hget("vmpooler__vm__#{vm}", 'pool_alias') if request_id
159
+ open_socket_error = redis.hget("vmpooler__vm__#{vm}", 'open_socket_error')
160
+ redis.smove("vmpooler__pending__#{pool}", "vmpooler__completed__#{pool}", vm)
161
+ if request_id
162
+ ondemandrequest_hash = redis.hgetall("vmpooler__odrequest__#{request_id}")
163
+ if ondemandrequest_hash && ondemandrequest_hash['status'] != 'failed' && ondemandrequest_hash['status'] != 'deleted'
164
+ # will retry a VM that did not come up as vm_ready? only if it has not been market failed or deleted
165
+ redis.zadd('vmpooler__odcreate__task', 1, "#{pool_alias}:#{pool}:1:#{request_id}")
166
+ end
167
+ end
168
+ $metrics.increment("errors.markedasfailed.#{pool}")
169
+ open_socket_error
170
+ end
171
+
153
172
  def move_pending_vm_to_ready(vm, pool, redis, request_id = nil)
154
173
  clone_time = redis.hget("vmpooler__vm__#{vm}", 'clone')
155
174
  finish = format('%<time>.2f', time: Time.now - Time.parse(clone_time))
@@ -197,11 +216,12 @@ module Vmpooler
197
216
 
198
217
  def vm_still_ready?(pool_name, vm_name, provider, redis)
199
218
  # Check if the VM is still ready/available
200
- return true if provider.vm_ready?(pool_name, vm_name)
219
+ return true if provider.vm_ready?(pool_name, vm_name, redis)
201
220
 
202
221
  raise("VM #{vm_name} is not ready")
203
222
  rescue StandardError
204
- move_vm_queue(pool_name, vm_name, 'ready', 'completed', redis, "is unreachable, removed from 'ready' queue")
223
+ open_socket_error = redis.hget("vmpooler__vm__#{vm_name}", 'open_socket_error')
224
+ move_vm_queue(pool_name, vm_name, 'ready', 'completed', redis, "removed from 'ready' queue. vm unreachable with error: #{open_socket_error}")
205
225
  end
206
226
 
207
227
  def check_ready_vm(vm, pool_name, ttl, provider)
@@ -318,7 +338,7 @@ module Vmpooler
318
338
  redis.hset("vmpooler__vm__#{vm}", 'user_tagged', 'true') if success
319
339
  end
320
340
 
321
- throw :stop_checking if provider.vm_ready?(pool, vm)
341
+ throw :stop_checking if provider.vm_ready?(pool, vm, redis)
322
342
 
323
343
  throw :stop_checking if provider.get_vm(pool, vm)
324
344
 
@@ -450,6 +470,9 @@ module Vmpooler
450
470
  ip_start = Time.now
451
471
  ip = provider.get_vm_ip_address(new_vmname, pool_name)
452
472
  ip_finish = format('%<time>.2f', time: Time.now - ip_start)
473
+
474
+ raise StandardError, "failed to obtain IP after #{ip_finish} seconds" if ip.nil?
475
+
453
476
  $logger.log('s', "[+] [#{pool_name}] Obtained IP for '#{new_vmname}' in #{ip_finish} seconds")
454
477
 
455
478
  @redis.with_metrics do |redis|
@@ -1248,19 +1271,20 @@ module Vmpooler
1248
1271
  end
1249
1272
  end
1250
1273
 
1251
- def check_pending_pool_vms(pool_name, provider, pool_check_response, inventory, pool_timeout)
1274
+ def check_pending_pool_vms(pool_name, provider, pool_check_response, inventory, pool_timeout, pool_timeout_notification)
1252
1275
  pool_timeout ||= $config[:config]['timeout'] || 15
1276
+ pool_timeout_notification ||= $config[:config]['timeout_notification'] || 5
1253
1277
  @redis.with_metrics do |redis|
1254
1278
  redis.smembers("vmpooler__pending__#{pool_name}").reverse.each do |vm|
1255
1279
  if inventory[vm]
1256
1280
  begin
1257
1281
  pool_check_response[:checked_pending_vms] += 1
1258
- check_pending_vm(vm, pool_name, pool_timeout, provider)
1282
+ check_pending_vm(vm, pool_name, pool_timeout, pool_timeout_notification, provider)
1259
1283
  rescue StandardError => e
1260
1284
  $logger.log('d', "[!] [#{pool_name}] _check_pool failed with an error while evaluating pending VMs: #{e}")
1261
1285
  end
1262
1286
  else
1263
- fail_pending_vm(vm, pool_name, pool_timeout, redis, exists: false)
1287
+ fail_pending_vm(vm, pool_name, pool_timeout, pool_timeout_notification, redis, exists: false)
1264
1288
  end
1265
1289
  end
1266
1290
  end
@@ -1387,7 +1411,7 @@ module Vmpooler
1387
1411
 
1388
1412
  check_ready_pool_vms(pool['name'], provider, pool_check_response, inventory, pool['ready_ttl'] || $config[:config]['ready_ttl'])
1389
1413
 
1390
- check_pending_pool_vms(pool['name'], provider, pool_check_response, inventory, pool['timeout'])
1414
+ check_pending_pool_vms(pool['name'], provider, pool_check_response, inventory, pool['timeout'], pool['timeout_notification'])
1391
1415
 
1392
1416
  check_completed_pool_vms(pool['name'], provider, pool_check_response, inventory)
1393
1417
 
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module Vmpooler
4
- VERSION = '3.3.0'
4
+ VERSION = '3.5.0'
5
5
  end
data/lib/vmpooler.rb CHANGED
@@ -82,6 +82,7 @@ module Vmpooler
82
82
  end
83
83
  parsed_config[:config]['clone_target'] = ENV['CLONE_TARGET'] if ENV['CLONE_TARGET']
84
84
  parsed_config[:config]['timeout'] = string_to_int(ENV['TIMEOUT']) if ENV['TIMEOUT']
85
+ parsed_config[:config]['timeout_notification'] = string_to_int(ENV['TIMEOUT_NOTIFICATION']) if ENV['TIMEOUT_NOTIFICATION']
85
86
  parsed_config[:config]['vm_lifetime_auth'] = string_to_int(ENV['VM_LIFETIME_AUTH']) if ENV['VM_LIFETIME_AUTH']
86
87
  parsed_config[:config]['max_tries'] = string_to_int(ENV['MAX_TRIES']) if ENV['MAX_TRIES']
87
88
  parsed_config[:config]['retry_factor'] = string_to_int(ENV['RETRY_FACTOR']) if ENV['RETRY_FACTOR']
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: vmpooler
3
3
  version: !ruby/object:Gem::Version
4
- version: 3.3.0
4
+ version: 3.5.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Puppet
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2023-08-16 00:00:00.000000000 Z
11
+ date: 2023-08-23 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  requirement: !ruby/object:Gem::Requirement