cem_acpt 0.7.3 → 0.8.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/.rubocop.yml +3 -1
- data/Gemfile.lock +42 -14
- data/README.md +8 -0
- data/cem_acpt.gemspec +3 -1
- data/exe/cem_acpt_image +0 -0
- data/lib/cem_acpt/action_result.rb +85 -0
- data/lib/cem_acpt/cli.rb +42 -22
- data/lib/cem_acpt/config/base.rb +4 -2
- data/lib/cem_acpt/goss/api.rb +8 -2
- data/lib/cem_acpt/image_builder.rb +64 -72
- data/lib/cem_acpt/logging.rb +41 -30
- data/lib/cem_acpt/platform.rb +4 -5
- data/lib/cem_acpt/provision/terraform/linux.rb +2 -2
- data/lib/cem_acpt/provision/terraform/terraform_cmd.rb +181 -0
- data/lib/cem_acpt/provision/terraform/windows.rb +9 -0
- data/lib/cem_acpt/provision/terraform.rb +34 -47
- data/lib/cem_acpt/provision.rb +1 -1
- data/lib/cem_acpt/puppet_helpers.rb +1 -1
- data/lib/cem_acpt/test_data.rb +3 -3
- data/lib/cem_acpt/test_runner/log_formatter/error_formatter.rb +33 -0
- data/lib/cem_acpt/test_runner/log_formatter.rb +10 -1
- data/lib/cem_acpt/test_runner.rb +151 -52
- data/lib/cem_acpt/utils/ssh.rb +2 -2
- data/lib/cem_acpt/utils/terminal.rb +1 -5
- data/lib/cem_acpt/utils/winrm_runner.rb +160 -0
- data/lib/cem_acpt/utils.rb +41 -1
- data/lib/cem_acpt/version.rb +1 -1
- data/lib/cem_acpt.rb +51 -21
- data/lib/terraform/gcp/windows/main.tf +26 -0
- metadata +46 -8
@@ -2,11 +2,11 @@
|
|
2
2
|
|
3
3
|
require 'fileutils'
|
4
4
|
require 'json'
|
5
|
-
require 'ruby-terraform'
|
6
5
|
require_relative 'logging'
|
7
6
|
require_relative 'platform'
|
8
7
|
require_relative 'utils'
|
9
8
|
require_relative 'version'
|
9
|
+
require_relative 'provision/terraform/terraform_cmd'
|
10
10
|
require_relative 'image_builder/exec'
|
11
11
|
require_relative 'image_builder/provision_commands'
|
12
12
|
|
@@ -18,11 +18,11 @@ module CemAcpt
|
|
18
18
|
|
19
19
|
builder = TerraformBuilder.new(config)
|
20
20
|
builder.run
|
21
|
-
logger.info('ImageBuilder') { "Image builder finished after #{builder.duration} seconds" }
|
21
|
+
logger.info('CemAcpt::ImageBuilder') { "Image builder finished after #{builder.duration} seconds" }
|
22
22
|
if builder.exit_code.zero?
|
23
|
-
logger.info('ImageBuilder') { 'Image builder finished successfully' }
|
23
|
+
logger.info('CemAcpt::ImageBuilder') { 'Image builder finished successfully' }
|
24
24
|
else
|
25
|
-
logger.error('ImageBuilder') { "Image builder finished with exit code #{builder.exit_code}" }
|
25
|
+
logger.error('CemAcpt::ImageBuilder') { "Image builder finished with exit code #{builder.exit_code}" }
|
26
26
|
end
|
27
27
|
exit builder.exit_code
|
28
28
|
end
|
@@ -55,42 +55,41 @@ module CemAcpt
|
|
55
55
|
|
56
56
|
def run
|
57
57
|
@start_time = Time.now
|
58
|
-
logger.
|
59
|
-
|
60
|
-
|
61
|
-
|
62
|
-
|
63
|
-
|
64
|
-
|
65
|
-
|
66
|
-
|
67
|
-
|
68
|
-
|
69
|
-
|
70
|
-
|
71
|
-
|
72
|
-
|
73
|
-
|
74
|
-
|
75
|
-
|
76
|
-
|
77
|
-
|
78
|
-
|
79
|
-
|
80
|
-
|
81
|
-
|
82
|
-
|
83
|
-
end
|
84
|
-
@exit_code = 0
|
58
|
+
logger.start_ci_group("CemAcptImage v#{CemAcpt::VERSION} run started at #{@start_time}")
|
59
|
+
@all_tfvars = new_tfvars(@config)
|
60
|
+
@linux_tfvars, @windows_tfvars = divide_tfvars_by_os(@all_tfvars)
|
61
|
+
image_types = []
|
62
|
+
image_types << [@linux_tfvars, 'linux'] unless no_linux?
|
63
|
+
image_types << [@windows_tfvars, 'windows'] unless no_windows?
|
64
|
+
return dry_run(image_types) if @config.get('dry_run')
|
65
|
+
|
66
|
+
@working_dir = new_working_dir
|
67
|
+
logger.info('CemAcpt::ImageBuilder') { "Using working directory: #{@working_dir}..." }
|
68
|
+
keep_terminal_alive
|
69
|
+
save_vars_to_file!('linux', @linux_tfvars)
|
70
|
+
save_vars_to_file!('windows', @windows_tfvars)
|
71
|
+
terraform_init
|
72
|
+
image_types.each do |tfvars, os_str|
|
73
|
+
terraform_plan(os_str, tfvars, DEFAULT_PLAN_NAME)
|
74
|
+
begin
|
75
|
+
terraform_apply(os_str, DEFAULT_PLAN_NAME)
|
76
|
+
output = JSON.parse(terraform_output(os_str, 'node-data', json: true))
|
77
|
+
output.each do |instance_name, data|
|
78
|
+
logger.info('CemAcpt::ImageBuilder') { "Stopping instance #{instance_name}..." }
|
79
|
+
@exec.run('compute', 'instances', 'stop', instance_name)
|
80
|
+
unless @config.get('no_build_images')
|
81
|
+
deprecate_old_images_in_family(data['image_family'])
|
82
|
+
create_image_from_disk(data['disk_link'], image_name_from_image_family(data['image_family']), data['image_family'])
|
85
83
|
end
|
86
|
-
|
87
|
-
terraform_destroy(os_str, tfvars) unless @config.get('no_destroy_nodes')
|
84
|
+
@exit_code = 0
|
88
85
|
end
|
86
|
+
ensure
|
87
|
+
terraform_destroy(os_str, tfvars) unless @config.get('no_destroy_nodes')
|
89
88
|
end
|
90
89
|
end
|
91
90
|
rescue StandardError => e
|
92
|
-
logger.error('
|
93
|
-
logger.verbose('
|
91
|
+
logger.error('CemAcpt::ImageBuilder') { "Image builder failed with error: #{e}" }
|
92
|
+
logger.verbose('CemAcpt::ImageBuilder') { e.backtrace.join("\n") }
|
94
93
|
@exit_code = 1
|
95
94
|
ensure
|
96
95
|
if @start_time
|
@@ -98,6 +97,7 @@ module CemAcpt
|
|
98
97
|
else
|
99
98
|
@duration = 0
|
100
99
|
end
|
100
|
+
logger.end_ci_group
|
101
101
|
end
|
102
102
|
|
103
103
|
private
|
@@ -109,21 +109,21 @@ module CemAcpt
|
|
109
109
|
end
|
110
110
|
|
111
111
|
def deprecate_old_images_in_family(image_family)
|
112
|
-
logger.info('
|
112
|
+
logger.info('CemAcpt::ImageBuilder') { "Deprecating old images in family #{image_family}..." }
|
113
113
|
images = @exec.run('compute', 'images', 'list', '--project', @config.get('platform.project'), '--filter', "family:#{image_family}")
|
114
114
|
images.each do |image|
|
115
115
|
next unless image['status'] == 'READY'
|
116
116
|
|
117
|
-
logger.info('
|
117
|
+
logger.info('CemAcpt::ImageBuilder') { "Deprecating image #{image['name']}..." }
|
118
118
|
@exec.run('compute', 'images', 'deprecate', image['name'], '--state', 'DEPRECATED', '--delete-in', '1d', '--project', @config.get('platform.project'))
|
119
119
|
end
|
120
120
|
end
|
121
121
|
|
122
122
|
def create_image_from_disk(disk_link, image_name, image_family)
|
123
|
-
logger.info('
|
123
|
+
logger.info('CemAcpt::ImageBuilder') { "Creating image from disk #{disk_link}..." }
|
124
124
|
@exec.run('compute', 'images', 'create', image_name, '--family', image_family,
|
125
125
|
'--source-disk', disk_link, '--project', @config.get('platform.project'))
|
126
|
-
logger.info('
|
126
|
+
logger.info('CemAcpt::ImageBuilder') { "Image #{image_name} created for family #{image_family}"}
|
127
127
|
end
|
128
128
|
|
129
129
|
def no_windows?
|
@@ -135,30 +135,22 @@ module CemAcpt
|
|
135
135
|
end
|
136
136
|
|
137
137
|
def dry_run(image_types)
|
138
|
-
logger.info('
|
138
|
+
logger.info('CemAcpt::ImageBuilder') { 'Dry run mode enabled. No images will be built.' }
|
139
139
|
image_types.each do |tfvars, os_str|
|
140
|
-
logger.info('
|
141
|
-
logger.info('
|
140
|
+
logger.info('CemAcpt::ImageBuilder') { "Dry run for #{os_str}..." }
|
141
|
+
logger.info('CemAcpt::ImageBuilder') { "Terraform vars:\n#{JSON.pretty_generate(tfvars)}" }
|
142
142
|
end
|
143
143
|
@exit_code = 0
|
144
144
|
end
|
145
145
|
|
146
146
|
def terraform
|
147
|
-
|
148
|
-
|
149
|
-
RubyTerraform.configure do |c|
|
150
|
-
c.logger = logger
|
151
|
-
c.stdout = logger
|
152
|
-
c.stderr = logger
|
153
|
-
end
|
154
|
-
@terraform = RubyTerraform
|
155
|
-
@terraform
|
147
|
+
@terraform ||= CemAcpt::Provision::TerraformCmd.new(@image_terraform_dir, @environment)
|
156
148
|
end
|
157
149
|
|
158
150
|
def new_environment(config)
|
159
151
|
env = (config.get('terraform.environment') || {})
|
160
152
|
env['CLOUDSDK_PYTHON_SITEPACKAGES'] = '1' # This is needed for gcloud to use numpy
|
161
|
-
logger.verbose('ImageBuilder') { "Using environment:\n#{JSON.pretty_generate(env)}" }
|
153
|
+
logger.verbose('CemAcpt::ImageBuilder') { "Using environment:\n#{JSON.pretty_generate(env)}" }
|
162
154
|
env
|
163
155
|
end
|
164
156
|
|
@@ -203,7 +195,7 @@ module CemAcpt
|
|
203
195
|
return unless block_given?
|
204
196
|
|
205
197
|
if no_os_str?(os_str)
|
206
|
-
logger.debug('ImageBuilder') { "Skipping #{os_str} because no_#{os_str} is true" }
|
198
|
+
logger.debug('CemAcpt::ImageBuilder') { "Skipping #{os_str} because no_#{os_str} is true" }
|
207
199
|
return
|
208
200
|
end
|
209
201
|
|
@@ -216,7 +208,7 @@ module CemAcpt
|
|
216
208
|
def terraform_init
|
217
209
|
raise 'Cannot initialize Terraform, both no_linux and no_windows are true' if no_linux? && no_windows?
|
218
210
|
|
219
|
-
logger.debug('ImageBuilder') { 'Initializing Terraform' }
|
211
|
+
logger.debug('CemAcpt::ImageBuilder') { 'Initializing Terraform' }
|
220
212
|
in_os_dir('linux') do
|
221
213
|
terraform.init({ input: false, no_color: true })
|
222
214
|
end
|
@@ -227,37 +219,37 @@ module CemAcpt
|
|
227
219
|
|
228
220
|
def terraform_plan(os_dir, tfvars, plan_name)
|
229
221
|
in_os_dir(os_dir) do
|
230
|
-
logger.debug('ImageBuilder') { "Creating Terraform plan #{plan_name} for #{os_dir}" }
|
231
|
-
logger.verbose('ImageBuilder') { "Using vars:\n#{JSON.pretty_generate(tfvars)}" }
|
222
|
+
logger.debug('CemAcpt::ImageBuilder') { "Creating Terraform plan #{plan_name} for #{os_dir}" }
|
223
|
+
logger.verbose('CemAcpt::ImageBuilder') { "Using vars:\n#{JSON.pretty_generate(tfvars)}" }
|
232
224
|
terraform.plan({ input: false, no_color: true, plan: plan_name, vars: tfvars }, { environment: environment })
|
233
225
|
end
|
234
226
|
end
|
235
227
|
|
236
228
|
def terraform_apply(os_dir, plan_name)
|
237
229
|
in_os_dir(os_dir) do
|
238
|
-
logger.debug('ImageBuilder') { "Applying Terraform plan #{plan_name} for #{os_dir}" }
|
230
|
+
logger.debug('CemAcpt::ImageBuilder') { "Applying Terraform plan #{plan_name} for #{os_dir}" }
|
239
231
|
terraform.apply({ input: false, no_color: true, plan: plan_name }, { environment: environment })
|
240
232
|
end
|
241
233
|
end
|
242
234
|
|
243
235
|
def terraform_output(os_dir, output_name, json: true)
|
244
236
|
in_os_dir(os_dir) do
|
245
|
-
logger.debug('ImageBuilder') { "Getting Terraform output #{output_name} for #{os_dir}" }
|
237
|
+
logger.debug('CemAcpt::ImageBuilder') { "Getting Terraform output #{output_name} for #{os_dir}" }
|
246
238
|
terraform.output({ no_color: true, json: json, name: output_name }, { environment: environment })
|
247
239
|
end
|
248
240
|
end
|
249
241
|
|
250
242
|
def terraform_destroy(os_dir, tfvars)
|
251
243
|
in_os_dir(os_dir) do
|
252
|
-
logger.debug('ImageBuilder') { "Destroying Terraform resources for #{os_dir}" }
|
253
|
-
logger.verbose('ImageBuilder') { "Using vars:\n#{JSON.pretty_generate(tfvars)}" }
|
244
|
+
logger.debug('CemAcpt::ImageBuilder') { "Destroying Terraform resources for #{os_dir}" }
|
245
|
+
logger.verbose('CemAcpt::ImageBuilder') { "Using vars:\n#{JSON.pretty_generate(tfvars)}" }
|
254
246
|
terraform.destroy({ auto_approve: true, input: false, no_color: true, vars: tfvars }, { environment: environment })
|
255
247
|
end
|
256
248
|
end
|
257
249
|
|
258
250
|
def terraform_show(os_dir)
|
259
251
|
in_os_dir(os_dir) do
|
260
|
-
logger.debug('ImageBuilder') { "Showing Terraform state for #{os_dir}" }
|
252
|
+
logger.debug('CemAcpt::ImageBuilder') { "Showing Terraform state for #{os_dir}" }
|
261
253
|
terraform.show({ no_color: true }, { environment: environment })
|
262
254
|
end
|
263
255
|
end
|
@@ -288,7 +280,7 @@ module CemAcpt
|
|
288
280
|
windows_image: windows_image?(image[:os]),
|
289
281
|
)
|
290
282
|
end
|
291
|
-
logger.verbose('ImageBuilder') { "All Terraform variables:\n#{JSON.pretty_generate(tfvars)}" }
|
283
|
+
logger.verbose('CemAcpt::ImageBuilder') { "All Terraform variables:\n#{JSON.pretty_generate(tfvars)}" }
|
292
284
|
tfvars
|
293
285
|
end
|
294
286
|
|
@@ -299,8 +291,8 @@ module CemAcpt
|
|
299
291
|
linux_tfvars[:node_data] = linux_node_data
|
300
292
|
windows_tfvars = tfvars.dup
|
301
293
|
windows_tfvars[:node_data] = windows_node_data
|
302
|
-
logger.verbose('ImageBuilder') { "Linux Terraform variables:\n#{JSON.pretty_generate(linux_tfvars)}" }
|
303
|
-
logger.verbose('ImageBuilder') { "Windows Terraform variables:\n#{JSON.pretty_generate(windows_tfvars)}" }
|
294
|
+
logger.verbose('CemAcpt::ImageBuilder') { "Linux Terraform variables:\n#{JSON.pretty_generate(linux_tfvars)}" }
|
295
|
+
logger.verbose('CemAcpt::ImageBuilder') { "Windows Terraform variables:\n#{JSON.pretty_generate(windows_tfvars)}" }
|
304
296
|
[linux_tfvars, windows_tfvars]
|
305
297
|
end
|
306
298
|
|
@@ -309,10 +301,10 @@ module CemAcpt
|
|
309
301
|
end
|
310
302
|
|
311
303
|
def save_vars_to_file!(prefix, vars)
|
312
|
-
logger.debug('ImageBuilder') { "Saving vars to file #{File.join(@working_dir, "#{prefix}_#{DEFAULT_VARS_FILE}")}" }
|
304
|
+
logger.debug('CemAcpt::ImageBuilder') { "Saving vars to file #{File.join(@working_dir, "#{prefix}_#{DEFAULT_VARS_FILE}")}" }
|
313
305
|
File.write(File.join(@working_dir, "#{prefix}_#{DEFAULT_VARS_FILE}"), vars.to_json)
|
314
306
|
rescue StandardError => e
|
315
|
-
logger.error('ImageBuilder') { 'Error saving vars to file' }
|
307
|
+
logger.error('CemAcpt::ImageBuilder') { 'Error saving vars to file' }
|
316
308
|
raise e
|
317
309
|
end
|
318
310
|
|
@@ -320,25 +312,25 @@ module CemAcpt
|
|
320
312
|
unless Dir.exist?(@image_terraform_dir)
|
321
313
|
raise "Image Terraform directory #{@image_terraform_dir} does not exist"
|
322
314
|
end
|
323
|
-
logger.debug('ImageBuilder') { "Creating new working directory in #{@image_terraform_dir}" }
|
315
|
+
logger.debug('CemAcpt::ImageBuilder') { "Creating new working directory in #{@image_terraform_dir}" }
|
324
316
|
working_dir = File.join(@image_terraform_dir, "image_builder_#{Time.now.to_i}")
|
325
317
|
FileUtils.mkdir_p(working_dir)
|
326
|
-
logger.verbose('ImageBuilder') { "Created working directory #{working_dir}" }
|
318
|
+
logger.verbose('CemAcpt::ImageBuilder') { "Created working directory #{working_dir}" }
|
327
319
|
FileUtils.cp_r(File.join(@image_terraform_dir, 'linux'), working_dir)
|
328
320
|
FileUtils.cp_r(File.join(@image_terraform_dir, 'windows'), working_dir)
|
329
|
-
logger.verbose('ImageBuilder') { "Copied Terraform files from #{@image_terraform_dir}/(linux|windows) to #{working_dir}" }
|
321
|
+
logger.verbose('CemAcpt::ImageBuilder') { "Copied Terraform files from #{@image_terraform_dir}/(linux|windows) to #{working_dir}" }
|
330
322
|
if File.exist?(@all_tfvars[:private_key])
|
331
323
|
FileUtils.cp(@all_tfvars[:private_key], working_dir)
|
332
324
|
@private_key = File.join(working_dir, File.basename(@all_tfvars[:private_key]))
|
333
|
-
logger.verbose('ImageBuilder') { "Copied private key #{@all_tfvars[:private_key]} to #{working_dir}" }
|
325
|
+
logger.verbose('CemAcpt::ImageBuilder') { "Copied private key #{@all_tfvars[:private_key]} to #{working_dir}" }
|
334
326
|
end
|
335
327
|
if File.exist?(@all_tfvars[:public_key])
|
336
328
|
FileUtils.cp(@all_tfvars[:public_key], working_dir)
|
337
329
|
@public_key = File.join(working_dir, File.basename(@all_tfvars[:public_key]))
|
338
|
-
logger.verbose('ImageBuilder') { "Copied public key #{@all_tfvars[:public_key]} to #{working_dir}" }
|
330
|
+
logger.verbose('CemAcpt::ImageBuilder') { "Copied public key #{@all_tfvars[:public_key]} to #{working_dir}" }
|
339
331
|
end
|
340
332
|
|
341
|
-
logger.verbose('ImageBuilder') { "Content of #{working_dir}:\n#{Dir.glob(File.join(working_dir, '*')).join("\n")}" }
|
333
|
+
logger.verbose('CemAcpt::ImageBuilder') { "Content of #{working_dir}:\n#{Dir.glob(File.join(working_dir, '*')).join("\n")}" }
|
342
334
|
working_dir
|
343
335
|
end
|
344
336
|
end
|
data/lib/cem_acpt/logging.rb
CHANGED
@@ -13,7 +13,7 @@ module CemAcpt
|
|
13
13
|
'error' => ::Logger::ERROR,
|
14
14
|
'fatal' => ::Logger::FATAL,
|
15
15
|
'unknown' => ::Logger::UNKNOWN,
|
16
|
-
}
|
16
|
+
}.freeze
|
17
17
|
|
18
18
|
# Delegator class for when you want to log to multiple devices
|
19
19
|
# at the same time, such as STDOUT and a file.
|
@@ -28,34 +28,39 @@ module CemAcpt
|
|
28
28
|
def self.from_logger_configs(configs)
|
29
29
|
return if configs.nil? || configs.empty?
|
30
30
|
|
31
|
-
|
31
|
+
logger_instances = configs.map do |config|
|
32
32
|
CemAcpt::Logging::Logger.new(config[:logdev],
|
33
33
|
config[:shift_age],
|
34
34
|
config[:shift_size],
|
35
35
|
**config.reject { |k, _| [:logdev, :shift_age, :shift_size].include?(k) })
|
36
36
|
end
|
37
|
-
new(*
|
37
|
+
new(*logger_instances)
|
38
38
|
end
|
39
39
|
|
40
|
-
def initialize(*
|
41
|
-
@loggers =
|
40
|
+
def initialize(*logger_instances)
|
41
|
+
@loggers = logger_instances
|
42
42
|
end
|
43
43
|
|
44
44
|
def logger_configs
|
45
|
-
|
45
|
+
loggers.map(&:config_hash)
|
46
46
|
end
|
47
47
|
|
48
48
|
def method_missing(m, *args, &block)
|
49
|
-
if
|
50
|
-
|
49
|
+
if loggers.all? { |l| l.respond_to?(m) }
|
50
|
+
loggers.map { |l| l.send(m, *args, &block) }
|
51
51
|
else
|
52
52
|
super
|
53
53
|
end
|
54
54
|
end
|
55
55
|
|
56
56
|
def respond_to_missing?(m, include_private = false)
|
57
|
-
|
57
|
+
loggers.all? { |l| l.respond_to?(m) } || super
|
58
58
|
end
|
59
|
+
|
60
|
+
private
|
61
|
+
|
62
|
+
# Basically just for making testing easier
|
63
|
+
attr_reader :loggers
|
59
64
|
end
|
60
65
|
|
61
66
|
# Delagator class for the standard Ruby Logger class.
|
@@ -89,55 +94,63 @@ module CemAcpt
|
|
89
94
|
end
|
90
95
|
|
91
96
|
def debug(progname = nil, &block)
|
92
|
-
|
93
|
-
return
|
97
|
+
severity = 'debug'
|
98
|
+
return log_trap_context(severity, progname, &block) if log_trap_context?(severity)
|
99
|
+
return log_ci_mode(severity, progname, &block) if log_ci_mode?(severity)
|
94
100
|
|
95
101
|
super
|
96
102
|
end
|
97
103
|
|
98
104
|
def info(progname = nil, &block)
|
99
|
-
|
100
|
-
return
|
105
|
+
severity = 'info'
|
106
|
+
return log_trap_context(severity, progname, &block) if log_trap_context?(severity)
|
107
|
+
return log_ci_mode(severity, progname, &block) if log_ci_mode?(severity)
|
101
108
|
|
102
109
|
super
|
103
110
|
end
|
104
111
|
|
105
112
|
def warn(progname = nil, &block)
|
106
|
-
|
107
|
-
return
|
113
|
+
severity = 'warn'
|
114
|
+
return log_trap_context(severity, progname, &block) if log_trap_context?(severity)
|
115
|
+
return log_ci_mode(severity, progname, &block) if log_ci_mode?(severity)
|
108
116
|
|
109
117
|
super
|
110
118
|
end
|
111
119
|
|
112
120
|
def error(progname = nil, &block)
|
113
|
-
|
114
|
-
return
|
121
|
+
severity = 'error'
|
122
|
+
return log_trap_context(severity, progname, &block) if log_trap_context?(severity)
|
123
|
+
return log_ci_mode(severity, progname, &block) if log_ci_mode?(severity)
|
115
124
|
|
116
125
|
super
|
117
126
|
end
|
118
127
|
|
119
128
|
def fatal(progname = nil, &block)
|
120
|
-
|
121
|
-
return
|
129
|
+
severity = 'fatal'
|
130
|
+
return log_trap_context(severity, progname, &block) if log_trap_context?(severity)
|
131
|
+
return log_ci_mode(severity, progname, &block) if log_ci_mode?(severity)
|
122
132
|
|
123
133
|
super
|
124
134
|
end
|
125
135
|
|
126
|
-
|
127
|
-
# @param name [String] the name of the group
|
128
|
-
def with_ci_group(name)
|
136
|
+
def start_ci_group(name)
|
129
137
|
if @ci_mode
|
130
138
|
self.<< "::group::#{name}\n"
|
131
139
|
else
|
132
140
|
info(name)
|
133
141
|
end
|
134
|
-
|
135
|
-
|
142
|
+
end
|
143
|
+
|
144
|
+
def end_ci_group
|
136
145
|
self.<< "::endgroup::\n" if @ci_mode
|
137
146
|
end
|
138
147
|
|
139
148
|
private
|
140
149
|
|
150
|
+
def log_trap_context?(severity)
|
151
|
+
@trap_context && level <= LEVEL_MAP[severity]
|
152
|
+
end
|
153
|
+
|
141
154
|
# Can't use the standard Logger methods when in trap context
|
142
155
|
# because they don't work. So we have to write directly to the
|
143
156
|
# raw logdev. Unlike the standard Logger methods, there is no
|
@@ -145,8 +158,6 @@ module CemAcpt
|
|
145
158
|
# This is necessary in the trap context because using a Mutex
|
146
159
|
# lock in a trap context will cause a deadlock.
|
147
160
|
def log_trap_context(severity, progname = nil, &block)
|
148
|
-
return false unless @trap_context && level <= LEVEL_MAP[severity]
|
149
|
-
|
150
161
|
if @raw_logdev.respond_to?(:puts)
|
151
162
|
@raw_logdev.puts(ci_format(severity, false, progname, &block))
|
152
163
|
elsif @raw_logdev.respond_to?(:write)
|
@@ -155,7 +166,10 @@ module CemAcpt
|
|
155
166
|
# Default to logging to STDERR
|
156
167
|
$stderr.puts(ci_format(severity, false, progname, &block))
|
157
168
|
end
|
158
|
-
|
169
|
+
end
|
170
|
+
|
171
|
+
def log_ci_mode?(severity)
|
172
|
+
@ci_mode && level <= LEVEL_MAP[severity]
|
159
173
|
end
|
160
174
|
|
161
175
|
# CI mode uses << instead of the standard Logger methods
|
@@ -164,10 +178,7 @@ module CemAcpt
|
|
164
178
|
# with a standard Logger, the CI mode messages are still
|
165
179
|
# formatted correctly.
|
166
180
|
def log_ci_mode(severity, progname = nil, &block)
|
167
|
-
return false unless @ci_mode && level <= LEVEL_MAP[severity]
|
168
|
-
|
169
181
|
self.<<(ci_format(severity, true, progname, &block))
|
170
|
-
true
|
171
182
|
end
|
172
183
|
|
173
184
|
# Formats the log message for CI mode, translating the severity
|
data/lib/cem_acpt/platform.rb
CHANGED
@@ -1,6 +1,5 @@
|
|
1
1
|
# frozen_string_literal: true
|
2
2
|
|
3
|
-
require 'concurrent-ruby'
|
4
3
|
require_relative 'logging'
|
5
4
|
|
6
5
|
# CemAcpt::Platform manages creating and configring platform specific objects
|
@@ -25,7 +24,7 @@ module CemAcpt::Platform
|
|
25
24
|
raise Error, 'run_data must include a :test_data key' unless run_data.key?(:test_data)
|
26
25
|
raise Error, 'run_data[:test_data] must be an Array' unless run_data[:test_data].is_a?(Array)
|
27
26
|
|
28
|
-
logger.info "Using #{platform} for #{run_data[:test_data].length} tests..."
|
27
|
+
logger.info('CemAcpt::Platform') { "Using #{platform} for #{run_data[:test_data].length} tests..." }
|
29
28
|
run_data[:test_data].dup.each_with_object([]) do |single_test_data, ary|
|
30
29
|
ary << new_test_platform_object(platform, config, single_test_data, **run_data.reject { |k, _| k == :test_data })
|
31
30
|
end
|
@@ -53,7 +52,7 @@ module CemAcpt::Platform
|
|
53
52
|
File.basename(file, '.rb') unless file.end_with?('base.rb')
|
54
53
|
end
|
55
54
|
@platforms.compact!
|
56
|
-
logger.debug "Discovered platform(s): #{@platforms}"
|
55
|
+
logger.debug('CemAcpt::Platform') { "Discovered platform(s): #{@platforms}" }
|
57
56
|
@platforms
|
58
57
|
end
|
59
58
|
|
@@ -83,7 +82,7 @@ module CemAcpt::Platform
|
|
83
82
|
require_relative 'platform/base'
|
84
83
|
# If the class has already been defined, we can just use it.
|
85
84
|
if Object.const_defined?(class_name)
|
86
|
-
logger.debug "Using existing platform class #{class_name}"
|
85
|
+
logger.debug('CemAcpt::Platform') { "Using existing platform class #{class_name}" }
|
87
86
|
klass = Object.const_get(class_name)
|
88
87
|
else
|
89
88
|
# Otherwise, we need to create the class. We do this by setting
|
@@ -110,7 +109,7 @@ module CemAcpt::Platform
|
|
110
109
|
end,
|
111
110
|
)
|
112
111
|
end
|
113
|
-
logger.debug "Using platform class: #{klass.inspect}"
|
112
|
+
logger.debug('CemAcpt::Platform') { "Using platform class: #{klass.inspect}" }
|
114
113
|
klass
|
115
114
|
end
|
116
115
|
end
|
@@ -53,8 +53,8 @@ module CemAcpt
|
|
53
53
|
'--logdest',
|
54
54
|
'console,/opt/cem_acpt/provision_apply.log',
|
55
55
|
]
|
56
|
-
cmd << '--debug' if @config.debug?
|
57
|
-
cmd << '--verbose' if @config.verbose?
|
56
|
+
cmd << '--debug' if @config.debug? && !@config.get('puppet.no_debug')
|
57
|
+
cmd << '--verbose' if @config.verbose? && !@config.get('puppet.no_verbose')
|
58
58
|
cmd << "#{destination_provision_directory}/#{puppet_manifest_file}"
|
59
59
|
cmd.join(' ')
|
60
60
|
end
|