brpm_content_framework 0.1.55

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.
Files changed (77) hide show
  1. checksums.yaml +15 -0
  2. data/.gitignore +38 -0
  3. data/.travis.yml +17 -0
  4. data/Gemfile +3 -0
  5. data/LICENSE +21 -0
  6. data/README.md +308 -0
  7. data/Rakefile +23 -0
  8. data/TO_BE_MIGRATED.txt +9 -0
  9. data/architecture.png +0 -0
  10. data/automations/direct_execute.meta +10 -0
  11. data/automations/direct_execute.rb +10 -0
  12. data/automations/install_module.meta +10 -0
  13. data/automations/install_module.rb +13 -0
  14. data/bin/brpm_install +30 -0
  15. data/bin/brpm_uninstall +30 -0
  16. data/bin/event_handler +63 -0
  17. data/bin/webhook_receiver +49 -0
  18. data/brpm_content.gemspec +31 -0
  19. data/config.yml +8 -0
  20. data/infrastructure/.bashrc +6 -0
  21. data/infrastructure/.brpm +2 -0
  22. data/infrastructure/config/customer_include.rb +26 -0
  23. data/infrastructure/config/server.yml +3 -0
  24. data/infrastructure/log.html +39 -0
  25. data/infrastructure/scripts/backup_database.sh +19 -0
  26. data/infrastructure/scripts/ddns.sh +10 -0
  27. data/infrastructure/scripts/install_brpm.sh +63 -0
  28. data/infrastructure/scripts/maintenance.sh +4 -0
  29. data/infrastructure/scripts/patch_brpm.sh +90 -0
  30. data/infrastructure/scripts/restore_database.sh +33 -0
  31. data/infrastructure/scripts/run_event_handler.cmd +19 -0
  32. data/infrastructure/scripts/run_event_handler.sh +20 -0
  33. data/infrastructure/scripts/run_webhook_receiver.cmd +15 -0
  34. data/infrastructure/scripts/run_webhook_receiver.sh +15 -0
  35. data/infrastructure/silent_install_options_4.6.txt +93 -0
  36. data/infrastructure/silent_install_options_upgrade_4.6.txt +92 -0
  37. data/infrastructure/smtp_settings.rb +42 -0
  38. data/lib/brpm_auto.rb +358 -0
  39. data/lib/brpm_script_executor.rb +80 -0
  40. data/lib/logging/brpm_logger.rb +39 -0
  41. data/lib/logging/logger_base.rb +36 -0
  42. data/lib/logging/simple_logger.rb +27 -0
  43. data/lib/module_installer.rb +483 -0
  44. data/lib/params/all_params.rb +80 -0
  45. data/lib/params/integration_settings.rb +27 -0
  46. data/lib/params/params.rb +174 -0
  47. data/lib/params/params_base.rb +81 -0
  48. data/lib/params/request_params.rb +38 -0
  49. data/lib/rest_api.rb +155 -0
  50. data/lib/semaphore.rb +79 -0
  51. data/lib/utilities.rb +317 -0
  52. data/lib/version_control/git.rb +192 -0
  53. data/lib/version_control/svn.rb +221 -0
  54. data/lib/write_to.rb +1 -0
  55. data/tests/all_params_spec.rb +116 -0
  56. data/tests/brpm_auto_spec.rb +84 -0
  57. data/tests/customer_include/config/customer_include.rb +10 -0
  58. data/tests/customer_include/config/server.yml +3 -0
  59. data/tests/customer_include_spec.rb +29 -0
  60. data/tests/gemspec_spec.rb +11 -0
  61. data/tests/module_installer_spec.rb +46 -0
  62. data/tests/params_spec.rb +172 -0
  63. data/tests/request_params_spec.rb +86 -0
  64. data/tests/server_yaml_spec.rb +19 -0
  65. data/tests/spec_helper.rb +64 -0
  66. data/to_be_migrated/brpm_framework.rb +88 -0
  67. data/to_be_migrated/customer_include_default.rb +25 -0
  68. data/to_be_migrated/local_jirb.rb +15 -0
  69. data/to_be_migrated/resource_framework.rb +211 -0
  70. data/transport/dispatch_baa.rb +355 -0
  71. data/transport/dispatch_base.rb +345 -0
  72. data/transport/dispatch_nsh.rb +248 -0
  73. data/transport/dispatch_ssh.rb +154 -0
  74. data/transport/transport_baa.rb +1095 -0
  75. data/transport/transport_nsh.rb +359 -0
  76. data/transport/transport_ssh.rb +220 -0
  77. metadata +204 -0
data/lib/brpm_auto.rb ADDED
@@ -0,0 +1,358 @@
1
+ require "bundler"
2
+ require "yaml"
3
+
4
+ class BrpmAuto
5
+ private_class_method :new
6
+
7
+ class << self
8
+ attr_reader :config
9
+ attr_reader :version
10
+ attr_reader :logger
11
+ attr_reader :params
12
+ attr_reader :request_params
13
+ attr_reader :all_params
14
+ attr_reader :integration_settings
15
+
16
+ attr_reader :framework_root_path
17
+
18
+ attr_reader :gems_root_path
19
+ attr_reader :gemfile_lock
20
+
21
+ def init
22
+ @framework_root_path = File.expand_path("#{File.dirname(__FILE__)}/..")
23
+
24
+ require "logging/brpm_logger"
25
+
26
+ require_libs_no_file_logging @framework_root_path
27
+
28
+ self.extend Utilities
29
+
30
+ @config = get_config
31
+ @version = @config["version"]
32
+
33
+ @gems_root_path = get_gems_root_path
34
+ end
35
+
36
+ def setup(params = {})
37
+ @params = Params.new(params)
38
+
39
+ load_server_params
40
+ load_customer_include_file
41
+
42
+ if @params.run_from_brpm
43
+ @logger = BrpmLogger.new
44
+ @request_params = RequestParams.new_for_request(@params.automation_results_dir, @params.application, @params.request_id)
45
+ else
46
+ initialize_logger(@params.log_file, @params.also_log_to_console)
47
+ initialize_request_params(@params.output_dir)
48
+ end
49
+
50
+ @all_params = AllParams.new(@params, @request_params)
51
+
52
+ if @params["SS_integration_dns"]
53
+ @integration_settings = IntegrationSettings.new(
54
+ @params["SS_integration_dns"],
55
+ @params["SS_integration_username"],
56
+ @params["SS_integration_password"],
57
+ @params["SS_integration_details"],
58
+ @params["SS_project_server"],
59
+ @params["SS_project_server_id"]
60
+ )
61
+ elsif defined?(SS_integration_dns)
62
+ @integration_settings = IntegrationSettings.new(
63
+ SS_integration_dns,
64
+ SS_integration_username,
65
+ SS_integration_password,
66
+ SS_integration_details,
67
+ SS_project_server,
68
+ SS_project_server_id
69
+ )
70
+ end
71
+ end
72
+
73
+ def require_module(module_name, module_version = nil)
74
+ module_version ||= get_latest_installed_version(module_name)
75
+ module_gem_path = get_module_gem_path(module_name, module_version)
76
+
77
+ if File.exists?(module_gem_path)
78
+ BrpmAuto.log "Found module #{module_name} #{module_version || ""} in gem path #{module_gem_path}."
79
+ else
80
+ raise Gem::GemNotFoundException, "Module #{module_name} version #{module_version} is not installed. Expected it on path #{module_gem_path}."
81
+ end
82
+
83
+ gemfile_lock_path = "#{module_gem_path}/Gemfile.lock"
84
+ if File.exists?(gemfile_lock_path) # TODO: decide how to react when multiple gems are 'required', each with a gemfile.lock
85
+ BrpmAuto.log "Found a Gemfile.lock: #{gemfile_lock_path} so parsing the specified version numbers for later usage..."
86
+ Dir.chdir(File.dirname(gemfile_lock_path)) do
87
+ @gemfile_lock = Bundler::LockfileParser.new(Bundler.read_file(gemfile_lock_path))
88
+ end
89
+ end
90
+
91
+ require_module_internal(module_name, module_version)
92
+ end
93
+
94
+ def require_libs_no_file_logging(module_path)
95
+ require_libs(module_path, false)
96
+ end
97
+
98
+ def require_libs(module_path, log = true)
99
+ lib_path = "#{module_path}/lib/**/*.rb"
100
+ require_files(Dir[lib_path], log)
101
+ end
102
+
103
+ def require_files(files, log = true)
104
+ failed_files = []
105
+ error_messages = []
106
+ files.each do |file|
107
+ if File.file?(file)
108
+ log ? (BrpmAuto.log "Loading #{file}...") : (print "Loading #{file}...\n")
109
+
110
+ begin
111
+ require file
112
+ rescue NameError => ne # when we require a set of files with inter-dependencies, the order is important, therefore we will retry the failed files later
113
+ failed_files << file
114
+ error_messages << ne
115
+ end
116
+ end
117
+ end
118
+ if failed_files.count > 0
119
+ if failed_files.count == files.count
120
+ raise NameError, "Following files failed loading: #{failed_files.join(", ")}\nError messages: #{error_messages.join(", ")}"
121
+ else
122
+ require_files(failed_files, log)
123
+ end
124
+ end
125
+ end
126
+
127
+ def load_server_params
128
+ server_config_file_path = "#{self.params.config_dir}/server.yml"
129
+ if File.exists?(server_config_file_path)
130
+ server_config = YAML.load_file(server_config_file_path)
131
+ server_config.each do |key, value|
132
+ @params[key] = value unless @params.has_key?(key)
133
+ end
134
+ end
135
+ end
136
+
137
+ def load_customer_include_file
138
+ customer_include_file_path = "#{self.params.config_dir}/customer_include.rb"
139
+ if File.exists?(customer_include_file_path)
140
+ load customer_include_file_path # use load instead of require to avoid having to restart BRPM after modifying the customer include file in a resource automation scenario
141
+ if defined?(get_customer_include_params)
142
+ customer_include_params = get_customer_include_params
143
+ customer_include_params.each do |key, value|
144
+ @params[key] = value
145
+ end
146
+ end
147
+ end
148
+ end
149
+
150
+ def initialize_logger(log_file, also_log_to_console = false)
151
+ @logger = SimpleLogger.new(log_file, also_log_to_console)
152
+ end
153
+
154
+ def run_from_brpm
155
+ @params.run_from_brpm
156
+ end
157
+
158
+ def log(message)
159
+ @logger.log(message)
160
+ end
161
+
162
+ def log_error(message)
163
+ @logger.log_error(message)
164
+ end
165
+
166
+ def message_box(message, m_type = "sep")
167
+ @logger.message_box(message, m_type)
168
+ end
169
+
170
+ def initialize_request_params(path)
171
+ @request_params = RequestParams.new(path)
172
+ end
173
+
174
+ def get_request_params_for_request(automation_results_dir, application, request_id)
175
+ RequestParams.new_for_request(automation_results_dir, application, request_id)
176
+ end
177
+
178
+ def initialize_integration_settings(dns, username, password, details)
179
+ @integration_settings = IntegrationSettings.new(dns, username, password, details)
180
+ end
181
+
182
+ def get_gems_root_path
183
+ if ENV["BRPM_CONTENT_HOME"]
184
+ ENV["BRPM_CONTENT_HOME"] # gemset location is overridden
185
+ elsif ENV["BRPM_HOME"]
186
+ "#{ENV["BRPM_HOME"]}/modules" # default gemset location when BRPM is installed
187
+ elsif ENV["GEM_HOME"]
188
+ ENV["GEM_HOME"] # default gemset location when BRPM is not installed
189
+ else
190
+ raise "Unable to find out the gems root path."
191
+ end
192
+ end
193
+
194
+ ###############################################################################################################################
195
+ # Assure backward compatibility with the ssh_script_header methods when running the automation scripts in a separate process
196
+ def set_property_flag(prop, value = nil)
197
+ acceptable_fields = ["name", "value", "environment", "component", "global", "private"]
198
+ flag = "#------ Block to Set Property ---------------#\n"
199
+ if value.nil?
200
+ flag += set_build_flag_data("properties", prop, acceptable_fields)
201
+ else
202
+ flag += "$$SS_Set_property{#{prop}=>#{value}}$$"
203
+ end
204
+ flag += "\n#------- End Set Property ---------------#\n"
205
+ BrpmAuto.log flag
206
+ flag
207
+ end
208
+
209
+ def set_server_flag(servers)
210
+ # servers = "server_name, env\ncserver2_name, env2"
211
+ acceptable_fields = ["name", "environment", "group"]
212
+ flag = "#------ Block to Set Servers ---------------#\n"
213
+ flag += set_build_flag_data("servers", servers, acceptable_fields)
214
+ flag += "\n#------ End Set Servers ---------------#\n"
215
+ BrpmAuto.log flag
216
+ flag
217
+ end
218
+
219
+ def set_component_flag(components)
220
+ # comps = "comp_name, version\ncomp2_name, version2"
221
+ flag = "#------ Block to Set Components ---------------#\n"
222
+ acceptable_fields = ["name", "version", "environment", "application"]
223
+ flag += set_build_flag_data("components", components, acceptable_fields)
224
+ flag += "\n#------ End Set Components ---------------#\n"
225
+ BrpmAuto.log flag
226
+ flag
227
+ end
228
+
229
+ def set_titles_acceptable?(cur_titles, acceptable_titles)
230
+ cur_titles.each.reject{ |cur| acceptable_titles.include?(cur)}.count == 0
231
+ end
232
+
233
+ def set_build_flag_data(set_item, set_data, acceptable_titles)
234
+ flag = ""; msg = ""
235
+ lines = set_data.split("\n")
236
+ titles = lines[0].split(",").map{ |it| it.strip }
237
+ if set_titles_acceptable?(titles, acceptable_titles)
238
+ flag += "$$SS_Set_#{set_item}{\n"
239
+ flag += "#{titles.join(", ")}\n"
240
+ lines[1..-1].each do |line|
241
+ if line.split(",").count == titles.count
242
+ flag += "#{line}\n"
243
+ else
244
+ msg += "Skipped: #{line}"
245
+ end
246
+ end
247
+ flag += "}$$\n"
248
+ else
249
+ flag += "ERROR - Unable to set #{set_item} - improper format\n"
250
+ end
251
+ flag += msg
252
+ end
253
+
254
+ def set_application_version(prop, value)
255
+ # set_application_flag(app_name, version)
256
+ flag = "#------ Block to Set Application Version ---------------#\n"
257
+ flag += "$$SS_Set_application{#{prop}=>#{value}}$$"
258
+ flag += "\n#------ End Set Application ---------------#\n"
259
+ BrpmAuto.log(flag)
260
+ flag
261
+ end
262
+
263
+ def pack_response(argument_name, response)
264
+ flag = "#------ Block to Set Pack Response ---------------#\n"
265
+ unless argument_name.nil?
266
+ if response.is_a?(Hash)
267
+ # Used for out-table output parameter
268
+ flag += "$$SS_Pack_Response{#{argument_name}@@#{response.to_json}}$$"
269
+ else
270
+ flag += "$$SS_Pack_Response{#{argument_name}=>#{response}}$$"
271
+ end
272
+ end
273
+ flag += "\n#------- End Set Pack Response Block ---------------#\n"
274
+ BrpmAuto.log flag
275
+ flag
276
+ end
277
+ ###############################################################################################################################
278
+
279
+ private
280
+
281
+ def require_module_internal(module_name, module_version)
282
+ module_path = get_module_gem_path(module_name, module_version)
283
+
284
+ module_config_file_path = "#{module_path}/config.yml"
285
+
286
+ if File.exist?(module_config_file_path)
287
+ module_config = YAML.load_file(module_config_file_path)
288
+
289
+ if module_config["dependencies"]
290
+ BrpmAuto.log "Loading the dependent modules..."
291
+ module_config["dependencies"].each do |dependency|
292
+ if dependency.is_a?(Hash)
293
+ dep_module_name = dependency.keys[0]
294
+ if @gemfile_lock
295
+ dep_module_version = get_version_from_gemfile_lock(dep_module_name)
296
+ else
297
+ dep_module_version = dependency.values[0]["version"]
298
+ end
299
+ else
300
+ dep_module_name = dependency
301
+
302
+ if @gemfile_lock
303
+ dep_module_version = get_version_from_gemfile_lock(dep_module_name)
304
+ else
305
+ dep_module_version = get_latest_installed_version(dep_module_name)
306
+ end
307
+ end
308
+
309
+ BrpmAuto.log "Loading module #{dep_module_name} version #{dep_module_version}..."
310
+ require_module_internal(dep_module_name, dep_module_version)
311
+ end
312
+ end
313
+ else
314
+ BrpmAuto.log "No config file found."
315
+ end
316
+
317
+ BrpmAuto.log "Loading the libraries of module #{module_name}..."
318
+ require_libs(module_path)
319
+
320
+ module_path
321
+ end
322
+
323
+ def get_config
324
+ YAML.load_file("#{@framework_root_path}/config.yml")
325
+ end
326
+
327
+ def get_module_gem_path(module_name, module_version)
328
+ "#{@gems_root_path}/gems/#{module_name}-#{module_version}"
329
+ end
330
+
331
+ def get_latest_installed_version(module_name)
332
+ latest_version_path = get_module_gem_path(module_name, "latest")
333
+ return "latest" if File.exists?(latest_version_path)
334
+
335
+ all_version_search = get_module_gem_path(module_name, "*")
336
+ version_paths = Dir.glob(all_version_search)
337
+
338
+ raise GemNoVersionsInstalledError, "Could not find any installed version of module #{module_name}. Expected them in #{get_module_gem_path(module_name, "*")}" if version_paths.empty?
339
+
340
+ versions = version_paths.map { |path| File.basename(path).sub("#{module_name}-", "") }
341
+
342
+ versions.sort{ |a, b| Gem::Version.new(a) <=> Gem::Version.new(b) }.last
343
+ end
344
+
345
+ def get_version_from_gemfile_lock(module_name)
346
+ spec = @gemfile_lock.specs.find { |spec| spec.name == module_name }
347
+ spec.version
348
+ end
349
+ end
350
+
351
+ self.init
352
+ end
353
+
354
+ class GemNoVersionsInstalledError < Gem::GemNotFoundException
355
+ end
356
+
357
+ class GemNotInstalledError < Gem::GemNotFoundException
358
+ end
@@ -0,0 +1,80 @@
1
+ require_relative "brpm_auto"
2
+
3
+ class BrpmScriptExecutor
4
+ class << self
5
+ def execute_automation_script(modul, name, params)
6
+ begin
7
+ BrpmAuto.setup(params)
8
+
9
+ BrpmAuto.log ""
10
+ BrpmAuto.log ">>>>>>>>>>>>>> START automation #{name}"
11
+ start_time = Time.now
12
+
13
+ BrpmAuto.log "Loading module #{modul}#{params["module_version"] ? " #{params["module_version"]}" : ""} and its dependencies..."
14
+ module_path = BrpmAuto.require_module(modul, params["module_version"])
15
+ BrpmAuto.log "Finished loading the module."
16
+
17
+ automation_script_path = "#{module_path}/automations/#{name}.rb"
18
+
19
+ BrpmAuto.log "Loading the automation script #{automation_script_path}..."
20
+ load automation_script_path
21
+
22
+ rescue Exception => e
23
+ BrpmAuto.log_error "#{e}"
24
+ BrpmAuto.log "\n\t" + e.backtrace.join("\n\t")
25
+
26
+ raise e
27
+ ensure
28
+ stop_time = Time.now
29
+ duration = 0
30
+ duration = stop_time - start_time unless start_time.nil?
31
+
32
+ BrpmAuto.log ">>>>>>>>>>>>>> STOP automation #{name} - total duration: #{Time.at(duration).utc.strftime("%H:%M:%S")}"
33
+ BrpmAuto.log ""
34
+
35
+ #load "#{File.dirname(__FILE__)}/write_to.rb" if BrpmAuto.params.run_from_brpm
36
+ end
37
+ end
38
+
39
+ alias_method :execute_automation_script_from_gem, :execute_automation_script
40
+
41
+ def execute_resource_automation_script(modul, name, params, parent_id, offset, max_records)
42
+ begin
43
+ BrpmAuto.setup(params)
44
+
45
+ BrpmAuto.log ""
46
+ BrpmAuto.log ">>>>>>>>>>>>>> START resource automation #{name}"
47
+ start_time = Time.now
48
+
49
+ BrpmAuto.log "Loading module #{modul} and its dependencies..."
50
+ module_path = BrpmAuto.require_module(modul) #TODO: from where should we get the module version of the script?
51
+ BrpmAuto.log "Finished loading the module."
52
+
53
+ automation_script_path = "#{module_path}/resource_automations/#{name}.rb"
54
+
55
+ BrpmAuto.log "Loading the resource automation script #{automation_script_path}..."
56
+ load automation_script_path
57
+
58
+ BrpmAuto.log "Calling execute_resource_automation_script(params, parent_id, offset, max_records)..."
59
+ execute_script(params, parent_id, offset, max_records)
60
+
61
+ rescue Exception => e
62
+ BrpmAuto.log_error "#{e}"
63
+ BrpmAuto.log "\n\t" + e.backtrace.join("\n\t")
64
+
65
+ raise e
66
+ ensure
67
+ stop_time = Time.now
68
+ duration = stop_time - start_time
69
+
70
+ BrpmAuto.log ">>>>>>>>>>>>>> STOP resource automation #{name} - total duration: #{Time.at(duration).utc.strftime("%H:%M:%S")}"
71
+ BrpmAuto.log ""
72
+
73
+ #load "#{File.dirname(__FILE__)}/write_to.rb" if BrpmAuto.params.run_from_brpm
74
+ end
75
+ end
76
+
77
+ alias_method :execute_resource_automation_script_from_gem, :execute_resource_automation_script
78
+ end
79
+ end
80
+
@@ -0,0 +1,39 @@
1
+ require_relative "logger_base"
2
+
3
+ class BrpmLogger < LoggerBase
4
+ attr_reader :request_log_file_path
5
+ attr_reader :step_run_log_file_path
6
+
7
+ def initialize
8
+ @step_number = BrpmAuto.params.step_number
9
+ @step_name = BrpmAuto.params.step_name
10
+
11
+ @request_log_file_path = "#{BrpmAuto.params.automation_results_dir}/#{BrpmAuto.params.request_id}.log"
12
+
13
+ # @step_run_log_file_path = "#{BrpmAuto.params.automation_results_dir}/#{BrpmAuto.params.request_id}_#{BrpmAuto.params.step_id}_#{BrpmAuto.params.run_key}.log"
14
+ @step_run_log_file_path = BrpmAuto.params.output_file
15
+
16
+ print "Logging to #{@step_run_log_file_path} and #{@request_log_file_path}\n" unless BrpmAuto.params.also_log_to_console
17
+ end
18
+
19
+ def log(message)
20
+ message = message.to_s # in case booleans or whatever are passed
21
+ timestamp = "#{Time.now.strftime("%Y-%m-%d %H:%M:%S")}"
22
+ log_message = ""
23
+
24
+ prefix = "#{timestamp}|#{'%2.2s' % @step_number}|#{'%-20.20s' % @step_name}|"
25
+ message.gsub!("\n", "\n" + (" " * prefix.length))
26
+
27
+ log_message = "#{prefix}#{message}\n"
28
+
29
+ File.open(@request_log_file_path, "a") do |log_file|
30
+ log_file.print(log_message)
31
+ end
32
+
33
+ File.open(@step_run_log_file_path, "a") do |log_file|
34
+ log_file.print(log_message)
35
+ end
36
+
37
+ print(log_message) if BrpmAuto.params.also_log_to_console
38
+ end
39
+ end
@@ -0,0 +1,36 @@
1
+ class LoggerBase
2
+ # Provides a pretty box for titles
3
+ #
4
+ # ==== Attributes
5
+ #
6
+ # * +msg+ - the text to output
7
+ # * +mtype+ - box type to display sep: a separator line, title a box around the message
8
+ def message_box(msg, mtype = "sep")
9
+ return "" if msg.nil? || msg.length < 1
10
+ tot = 72
11
+ msg = msg[0..64] if msg.length > 65
12
+
13
+ ilen = tot - msg.length
14
+
15
+ if mtype == "sep"
16
+ start = "##{"-" * (ilen/2).to_i} #{msg} "
17
+ res = "#{start}#{"-" * (tot- start.length + 1)}#"
18
+ else
19
+ res = "##{"-" * tot}#\n"
20
+ start = "##{" " * (ilen/2).to_i} #{msg} "
21
+ res += "#{start}#{" " * (tot- start.length + 1)}#\n"
22
+ res += "##{"-" * tot}#\n"
23
+ end
24
+
25
+ log(res)
26
+ end
27
+
28
+ def log_error(message)
29
+ log ""
30
+ log "******** ERROR ********"
31
+ log "An error has occurred"
32
+ log "#{message}"
33
+ log "***********************"
34
+ log ""
35
+ end
36
+ end
@@ -0,0 +1,27 @@
1
+ require_relative "logger_base"
2
+
3
+ class SimpleLogger < LoggerBase
4
+ def initialize(log_file, also_log_to_console = false)
5
+ @log_file = log_file
6
+ @also_log_to_console = also_log_to_console
7
+
8
+ print "Logging to #{@log_file}\n" unless also_log_to_console
9
+ end
10
+
11
+ def log(message)
12
+ message = message.to_s # in case booleans or whatever are passed
13
+ timestamp = "#{Time.now.strftime("%Y-%m-%d %H:%M:%S")}"
14
+ log_message = ""
15
+
16
+ prefix = "#{timestamp}|"
17
+ message = message.gsub("\n", "\n" + (" " * prefix.length))
18
+
19
+ log_message = "#{prefix}#{message}\n"
20
+
21
+ File.open(@log_file, "a") do |log_file|
22
+ log_file.print(log_message)
23
+ end
24
+
25
+ print(log_message) if @also_log_to_console
26
+ end
27
+ end