opensecret 0.0.2 → 0.0.4

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 (44) hide show
  1. checksums.yaml +4 -4
  2. data/Gemfile +4 -0
  3. data/README.md +2 -2
  4. data/bin/opensecret +3 -6
  5. data/lib/opensecret-domain.ini +23 -0
  6. data/lib/opensecret.rb +30 -2
  7. data/lib/opensecret/additions/array.rb +117 -0
  8. data/lib/opensecret/additions/dir.rb +35 -0
  9. data/lib/opensecret/additions/string.rb +312 -0
  10. data/lib/opensecret/commons/eco.cmdline.rb +446 -0
  11. data/lib/opensecret/commons/eco.faculty.rb +364 -0
  12. data/lib/opensecret/commons/eco.system.rb +437 -0
  13. data/lib/opensecret/commons/eco.systems.rb +98 -0
  14. data/lib/opensecret/{safe.rb → delegate.rb} +4 -2
  15. data/lib/opensecret/eco.do.rb +46 -0
  16. data/lib/opensecret/executors/crypt.keys/crypt.keys.ini +79 -0
  17. data/lib/opensecret/executors/crypt.keys/crypt.keys.rb +68 -0
  18. data/lib/opensecret/executors/decrypt/decrypt.ini +64 -0
  19. data/lib/opensecret/executors/decrypt/decrypt.rb +49 -0
  20. data/lib/opensecret/executors/encrypt/encrypt.ini +55 -0
  21. data/lib/opensecret/executors/encrypt/encrypt.rb +82 -0
  22. data/lib/opensecret/factbase/hub-runtime.ini +123 -0
  23. data/lib/opensecret/factbase/known-hosts.ini +75 -0
  24. data/lib/opensecret/factbase/published.facts/blobbolicious-facts.ini +553 -0
  25. data/lib/opensecret/factbase/published.facts/credential-facts.ini +40 -0
  26. data/lib/opensecret/factbase/published.facts/infrastructure-facts.ini +63 -0
  27. data/lib/opensecret/factbase/readme.md +24 -0
  28. data/lib/opensecret/factbase/retired.facts/maven.database.ide.facts.ini +127 -0
  29. data/lib/opensecret/factbase/retired.facts/s3-upload-block-facts.ini +17 -0
  30. data/lib/opensecret/plugins.io/cipher/crypto.rb +174 -0
  31. data/lib/opensecret/plugins.io/error/eco.exceptions.rb +24 -0
  32. data/lib/opensecret/plugins.io/facts/fact.chars.rb +66 -0
  33. data/lib/opensecret/plugins.io/facts/fact.factor.rb +156 -0
  34. data/lib/opensecret/plugins.io/facts/fact.locator.rb +105 -0
  35. data/lib/opensecret/plugins.io/facts/fact.reader.rb +137 -0
  36. data/lib/opensecret/plugins.io/facts/fact.tree.rb +661 -0
  37. data/lib/opensecret/plugins.io/file/file.rb +483 -0
  38. data/lib/opensecret/plugins.io/git/git.flow.rb +388 -0
  39. data/lib/opensecret/plugins.io/logs/log.object.rb +89 -0
  40. data/lib/opensecret/plugins.io/logs/logging.rb +203 -0
  41. data/lib/opensecret/plugins.io/time/time.stamp.rb +425 -0
  42. data/lib/opensecret/version.rb +2 -2
  43. data/opensecret.gemspec +8 -13
  44. metadata +68 -18
@@ -0,0 +1,661 @@
1
+ #!/usr/bin/ruby
2
+
3
+ # --
4
+ # -- -----------------
5
+ # -- Fact Production
6
+ # -- -----------------
7
+ # --
8
+ # -- The fact tree is tasked with fact production
9
+ # -- (population). Fact production is done by [consuming]
10
+ # --
11
+ # -- [1] - simple string, number of boolean facts
12
+ # -- [2] - facts already produced
13
+ # -- [3] - identity facts from command line and environment
14
+ # -- [4] - software (behaviour) that derives facts
15
+ # -- [5] - inherited (extended) facts from (OO) parents
16
+ # --
17
+ # --
18
+ # --
19
+ # -- -----------------------------------------
20
+ # -- The 4 Universal (DevOps) Creation Facts
21
+ # -- -----------------------------------------
22
+ # --
23
+ # -- No matter the (DevOps) eco-system being fabricated, these four
24
+ # -- facts prevail and stand out.
25
+ # --
26
+ # -- Every time a DevOps [eco-system] is created, cloned, or recovered,
27
+ # -- a small cluster of core facts endure to define the instance and act
28
+ # -- as the identification basis of all new eco-system resources.
29
+ # --
30
+ # -- The 4 facts underpinning eco-system creation are
31
+ # --
32
+ # -- [1] - [what] is being built
33
+ # -- [2] - [when] did the building begin
34
+ # -- [3] - [who] instigated it (and from)
35
+ # -- [4] - [which] workstation.
36
+ # --
37
+ # -- ---------------------------------------
38
+ # -- DevOps 4 Creational [Instance] Facts
39
+ # -- ---------------------------------------
40
+ # --
41
+ # -- The core instance identities used and reused time and again relate to
42
+ # --
43
+ # -- [1] - plugin (eg) wordpress.hub or jenkins.hub
44
+ # -- [2] - time (eg) 18036.0952.065
45
+ # -- [3] - user (eg) peterpan
46
+ # -- [4] - workstation (eg) laptop_susie or hp_desktop
47
+ # --
48
+ # --
49
+ class FactTree
50
+ include Singleton
51
+
52
+ @@eval_prefix = "e>>"
53
+ attr_reader :i, :f
54
+
55
+ # --
56
+ # -- Initialize the internal fact database
57
+ # -- which is exposed for fact consumption
58
+ # -- via
59
+ # --
60
+ # -- @i => [identity] facts (1D)
61
+ # -- @n => (reserved perhaps 4 nested facts)
62
+ # -- @f => [file facts] database (2D)
63
+ # -- @a => (reserved)
64
+ # -- @c => coded consumtion (in software)
65
+ # -- @t => template placeholders (2D)
66
+ # -- @s => sibling (same category) facts (1D)
67
+ # --
68
+ def instantiate plugin_id, plugin_folder
69
+
70
+ @i = { :plugin => plugin_id,
71
+ :time => Stamp.yyjjj_hhmm_sst,
72
+ :user => Home.usr,
73
+ :src_dir => plugin_folder,
74
+ :station => nil
75
+ }
76
+
77
+ @f = {}
78
+
79
+ @s = {}
80
+
81
+ @f.store symbol(plugin_id), {}
82
+ @p = @f[symbol(plugin_id)]
83
+
84
+
85
+ end
86
+
87
+
88
+
89
+ #--
90
+ #-- Set the main directory path.
91
+ #-- This method adds the parameter path to
92
+ #-- the identity map. After this method
93
+ #-- executes you will be able to access the
94
+ #-- directory with @i[:dir]
95
+ #--
96
+ def add_dir_to_identity key_directory
97
+ @i[:dir] = key_directory
98
+ end
99
+
100
+
101
+
102
+ # --
103
+ # --
104
+ # --
105
+ def assimilate_plugin_facts
106
+
107
+ plugin_fact_filepath = File.join @i[:src_dir], "#{@i[:plugin]}.ini"
108
+ log.info(ere) { "Plugin Factfile => #{plugin_fact_filepath}" }
109
+ assimilate_ini_file plugin_fact_filepath
110
+
111
+ end
112
+
113
+
114
+ # --
115
+ # --
116
+ # --
117
+ def assimilate_general_facts
118
+
119
+ facts_folder = fact_path("published.facts")
120
+
121
+ factfiles_map = Files.in_folders( Array.new.push(facts_folder) )
122
+ factfiles_map.each do |file_name, folder_name|
123
+
124
+ log.info(ere) {"Assimilating facts from => [#{file_name}]"}
125
+ factfile_path = File.join factfiles_map[file_name], file_name
126
+ log.info(ere) {"Factfile location => [#{nickname factfile_path}]"}
127
+ assimilate_ini_file factfile_path
128
+
129
+ end
130
+
131
+ end
132
+
133
+
134
+ # --
135
+ # -- Assimilate [[ hub-runtime.ini ]]
136
+ # -- This factfile builds upon the (fundamental) handful of
137
+ # -- identity facts. It derives the facts for
138
+ # --
139
+ # -- - the plugin instance folder
140
+ # -- - the instance stamp id keys
141
+ # --
142
+ # -- The instance fact file is not allowed to harbour any
143
+ # -- external dependencies.
144
+ # --
145
+ def assimilate_instance_facts
146
+
147
+ instance_facts_file = fact_path("hub-runtime.ini")
148
+ log.info(ere) { "Path to instance facts file => #{instance_facts_file}" }
149
+ assimilate_ini_file instance_facts_file
150
+
151
+ end
152
+
153
+
154
+ # --
155
+ # -- -----------------------------------
156
+ # -- Finding the Workstation (Category)
157
+ # -- -----------------------------------
158
+ # --
159
+ # -- The known hosts facts file is parsed with each
160
+ # -- section [examined] by asking two (2) questions.
161
+ # --
162
+ # -- [1] - is [username] this workstation's username?
163
+ # -- [2] - does [hostnames] include this hostname?
164
+ # --
165
+ # -- The 1st section to answer [YES] to both questions
166
+ # -- is deemed as our workstation. Its symbol header is
167
+ # -- then used for assimilation - how?
168
+ # --
169
+ # -- ----------------------------------------
170
+ # -- Assimilating Workstation Specific Facts
171
+ # -- ----------------------------------------
172
+ # --
173
+ # -- We do NOT assimilate the whole file.
174
+ # -- We simply assimilate the [SECTION] of the file
175
+ # -- that is deemed to be OUR (this) workstation.
176
+ # --
177
+ # -- -------------------------------------------
178
+ # -- Dependency Constraints | Workstation Facts
179
+ # -- -------------------------------------------
180
+ # --
181
+ # -- (work)station facts can [only] depend on facts that
182
+ # -- have been declared in [[ hub-runtime.ini ]]. No
183
+ # -- other external fact dependencies are permitted.
184
+ # --
185
+ def identify_my_workstation
186
+
187
+ workstation_factfile_name = "known-hosts.ini"
188
+ log_begin_workstation_identification workstation_factfile_name
189
+ stations_factfile = fact_path workstation_factfile_name
190
+ log.info(ere) { "Workstations Facts File (Path) => #{nickname stations_factfile}" }
191
+
192
+ our_user = Home.usr
193
+ our_host = NetDns.instance.host_name
194
+ log.info(ere){ "Station Search For => #{our_user}@#{our_host}" }
195
+
196
+ workstations = IniFile.load stations_factfile
197
+ workstations.each_section do |station|
198
+
199
+ no_user = "Workstation [#{station}] has no [username] fact."
200
+ raise RuntimeError.new no_user unless workstations[station].has_key? "username"
201
+
202
+ has_hostnames = workstations[station].has_key? "hostnames"
203
+ no_hostnames = "[#{station}] not a workstation as no [hostnames] fact - Skip!"
204
+ log.warn(ere) { no_hostnames } unless has_hostnames
205
+ next unless has_hostnames
206
+
207
+ this_user = evaluate(workstations[station]["username"])
208
+ these_hosts = evaluate(workstations[station]["hostnames"])
209
+ match = this_user.eql?(our_user) && these_hosts.include?(our_host)
210
+
211
+ log.info(ere){ "[#{station}] with #{this_user}@#{these_hosts} - No!" } unless match
212
+ next unless match
213
+
214
+ log.info(ere){ "[#{station}] with #{this_user}@#{these_hosts} - Matched!" }
215
+ dup_msg = "Duplicate or repeat match disallowed! #{@i[:station]} and #{station}"
216
+ raise RuntimeError.new dup_msg unless @i[:station].nil?
217
+
218
+ @i[:station] = station
219
+ @i[:workstation] = station.gsub(".", "_").to_sym
220
+
221
+ end
222
+
223
+ no_match_msg = "No workstation match made for [#{our_user}@#{our_host}]."
224
+ raise RuntimeError.new no_match_msg if @i[:station].nil?
225
+ log_end_workstation_identification workstation_factfile_name
226
+ LogObject.map @i
227
+
228
+ end
229
+
230
+
231
+ #--
232
+ #-- Knowing and setting @i[:workstation] to our workstation is key.
233
+ #-- This means that the other workstations can reference files in
234
+ #-- each others drives without knowing which workstation is being
235
+ #-- used (see ssh.keyfile for a ghost reference example).
236
+ #--
237
+ #-- Now we can proceed to assimilate the entire station facts file.
238
+ #--
239
+ def assimilate_station_facts
240
+
241
+ stations_factfile = fact_path "known-hosts.ini"
242
+ assimilate_ini_file stations_factfile
243
+
244
+ end
245
+
246
+
247
+ # --
248
+ # -- Get the path to a fact file or folder within the
249
+ # -- reusable facts source tree.
250
+ # --
251
+ # -- The base directory is acquired by dropping down
252
+ # -- three (3) directory levels from where this module
253
+ # -- is and then going into reusable.facts and finally
254
+ # -- appending the parameter path (file or folder).
255
+ # --
256
+ def fact_path fact_filename
257
+ fact_basedir = File.dirname( File.dirname( File.dirname( __FILE__ ) ) )
258
+ return File.join( File.join(fact_basedir,"reusable.facts"), fact_filename )
259
+ end
260
+
261
+
262
+ # --
263
+ # -- Call instantiate() before calling populate().
264
+ # --
265
+ # -- This method assimilates any and all fact files
266
+ # -- (recursively) found in two subdirectories
267
+ # --
268
+ # -- [1] - "reusable facts" and
269
+ # -- [2] - the [plugin] folder
270
+ # --
271
+ def self.populate
272
+
273
+ end
274
+
275
+
276
+ # -- -------------------------------------------------------------- -- #
277
+ # -- Eval and return result of parameter string if it is ruby code. -- #
278
+ # -- -------------------------------------------------------------- -- #
279
+ def evaluate string
280
+
281
+ # -----> @todo raise a FactError here
282
+
283
+ raise RuntimeError.new "Fact to Evaluate is Nil." if string.nil?
284
+ return string unless string.start_with? @@eval_prefix
285
+ return eval( string.gsub @@eval_prefix, "" )
286
+
287
+ end
288
+
289
+
290
+ # ----> -------------------------------------------------->
291
+ # ----> How to Write a Custom Error
292
+ # ----> -------------------------------------------------->
293
+ # ----> Add a custom data attributes to your exception
294
+ # ----> You can add custom data to your exception just like you'd do it in any other class. Let's add an attribute reader to our class and update the constructor.
295
+ # ----> class MyError < StandardError
296
+ # ----> attr_reader :thing
297
+ # ----> def initialize(msg="My default message", thing="apple")
298
+ # ----> @thing = thing
299
+ # ----> super(msg)
300
+ # ----> end
301
+ # ----> end
302
+ # ----> -------------------------------------------------->
303
+ # ----> Using the Custom Error Class
304
+ # ----> -------------------------------------------------->
305
+ # ----> begin
306
+ # ----> raise MyError.new("my message", "my thing")
307
+ # ----> rescue => e
308
+ # ----> puts e.thing # "my thing"
309
+ # ----> end
310
+ # ----> -------------------------------------------------->
311
+
312
+
313
+ # -- ---------------------------------------- -- #
314
+ # -- Add a fact to the main 2D fact database. -- #
315
+ # -- ---------------------------------------- -- #
316
+ def add_fact group_symbol, key_symbol, key_value
317
+
318
+ nil_error_text = "Neither fact coordinates nor value can be nil. [group]=> #{group_symbol} [key]=> #{key_symbol} [value]=> #{key_value}"
319
+ raise ArgumentError.new nil_error_text if group_symbol.nil? || key_symbol.nil? || key_value.nil?
320
+
321
+ if @f.has_key? group_symbol then
322
+
323
+ # --
324
+ # -- This isn't the first fact within this group
325
+ # -- so store the new fact key/value pair within
326
+ # -- the group's namespace.
327
+ # --
328
+ @f[group_symbol][key_symbol] = key_value
329
+
330
+ else
331
+
332
+ # --
333
+ # -- Create a new umbrella grouping against which
334
+ # -- the new key-value pairing will be inserted.
335
+ # --
336
+ @f.store group_symbol, { key_symbol => key_value }
337
+
338
+ end
339
+
340
+ # --
341
+ # -- The @s sibling hash is updated to reflect the
342
+ # -- key-value pairs within the current group. This
343
+ # -- allows @s to be used as shorthand within INI
344
+ # -- file fact definition statements.
345
+ # --
346
+ @s = @f[group_symbol]
347
+
348
+ end
349
+
350
+
351
+ # -- ------------------------------------------- -- #
352
+ # -- -- #
353
+ # -- Template -- #
354
+ # -- -- #
355
+ # -- The longest river in africa is without -- #
356
+ # -- doubt the @[africa|longest.river]. Now -- #
357
+ # -- @[south.america|most.spoken] is the -- #
358
+ # -- most common language in south america. -- #
359
+ # -- -- #
360
+ # -- The population of the americas -- #
361
+ # -- is @[americas|population] according to
362
+ # -- the Harvard 2015 census.
363
+ # -- -- #
364
+ # -- ------------------------------------------- -- #
365
+ # -- -- #
366
+ # -- Ruby Code -- #
367
+ # -- -- #
368
+ # -- double_north_america_pop = @f[:north_america][:population] * 2
369
+ # -- -- #
370
+ # -- ------------------------------------------- -- #
371
+ # -- Parameters -- #
372
+ # -- factory_facts : instantiated 2D hash -- #
373
+ # -- ini_filepath : path to factfile to read -- #
374
+ # -- -- #
375
+ # -- Dependencies and Assumptions -- #
376
+ # -- the [inifile] gem is installed -- #
377
+ # -- file exists at the ini_filepath -- #
378
+ # -- factory_facts are instantiated -- #
379
+ # -- identity facts like @i[:plugin] exist -- #
380
+ # -- ------------------------------------------- -- #
381
+ def assimilate_ini_file ini_filepath
382
+
383
+ fact_filename = File.basename ini_filepath
384
+ log_begin fact_filename
385
+
386
+ no_file = "No (ini) factfile found here => #{ini_filepath}"
387
+ raise ArgumentError.new no_file unless File.exists? ini_filepath
388
+
389
+ # --
390
+ # -- Use the inifile gem to parse and read the fact
391
+ # -- file contents into Ruby's map structures.
392
+ # --
393
+ begin
394
+
395
+ map_facts = IniFile.load ini_filepath
396
+
397
+ rescue Exception => e
398
+
399
+ log.fatal(ere) { "## ############################ #################################" }
400
+ log.fatal(ere) { "## Fact File Assimilation Error #################################" }
401
+ log.fatal(ere) { "## ############################ #################################" }
402
+ log.fatal(ere) { "## File => #{ini_filepath}" }
403
+ log.fatal(ere) { "## ############################ #################################" }
404
+
405
+ log.fatal(ere) { e.message }
406
+ log.fatal(ere) { e.backtrace.inspect }
407
+
408
+ exit
409
+
410
+ end
411
+
412
+ # -- ------------------------------------------------------------ -- #
413
+ # -- Copy all ini file facts to the global eco dictionary using a -- #
414
+ # -- format of ==] group_id.key_id = value -- #
415
+ # -- ------------------------------------------------------------ -- #
416
+ map_facts.each do | group_str, key_str, input_value |
417
+
418
+ assimilate_fact group_str, key_str, input_value
419
+
420
+ end
421
+
422
+ log_end fact_filename
423
+
424
+ end
425
+
426
+
427
+
428
+ def assimilate_fact group_str, key_str, input_value
429
+
430
+ grp_symbol = group_str.gsub(".", "_").to_sym
431
+ key_symbol = key_str.gsub(".", "_").to_sym
432
+
433
+ Throw.if_nil input_value
434
+ fact_val = input_value.strip
435
+
436
+ begin
437
+
438
+ unless discard_fact?( group_str, key_str, fact_val )
439
+ eval_value = evaluate(get_fact_value(fact_val))
440
+ add_fact grp_symbol, get_key_symbol(key_str), eval_value
441
+ end
442
+
443
+ rescue Exception => e
444
+
445
+ log.fatal(ere) { "## ##################### #################################" }
446
+ log.fatal(ere) { "## Fact Evaluation Error #################################" }
447
+ log.fatal(ere) { "## ##################### #################################" }
448
+ log.fatal(ere) { "## Fact Family => #{group_str}" }
449
+ log.fatal(ere) { "## Fact Key => #{key_str}" }
450
+ log.fatal(ere) { "## Fact Stmt => #{fact_val}" }
451
+ log.fatal(ere) { "## ##################### #################################" }
452
+
453
+ log.fatal(ere) { e.message }
454
+ log.fatal(ere) { e.backtrace.inspect }
455
+
456
+ raise e
457
+
458
+ end
459
+
460
+ unless @f.has_key? grp_symbol then
461
+
462
+ log.debug(ere){ "# -- ---------------------------------------------------------- #" }
463
+ log.debug(ere){ "# -- the [#{group_str}] silo facts." }
464
+ log.debug(ere){ "# -- ---------------------------------------------------------- #" }
465
+
466
+ end
467
+
468
+ id_keystring = "#{grp_symbol}#{key_symbol}".downcase
469
+ sensitive = id_keystring.includes_any? [ "secret", "password", "credential", "creds" ]
470
+ print_value = "****************"
471
+ print_value = eval_value unless sensitive
472
+
473
+ # -- -------------------------------------------------------- -- #
474
+ # -- Log the human readable (fixed-width) key and value pair. -- #
475
+ # -- -------------------------------------------------------- -- #
476
+ fw_key = sprintf '%-33s', "@f[:#{grp_symbol}][:#{key_symbol}]"
477
+ log.debug(ere){ "#{fw_key} => #{print_value}" }
478
+
479
+ end
480
+
481
+
482
+ def discard_fact? group_str, key_str, input_value
483
+
484
+ is_if = key_str.strip.end_with? "(if)"
485
+ is_unless = key_str.strip.end_with?("(un)") || key_str.strip.end_with?("(unless)")
486
+ return false unless is_if || is_unless
487
+
488
+ two_parts = input_value.split( @@eval_prefix )
489
+ no_prefix = "Conditional must be followed by eval prefix => #{two_parts}"
490
+ raise RuntimeError.new no_pefix unless two_parts.length == 2
491
+
492
+ conditional_part = two_parts.first.strip
493
+ no_curlies_msg = "Wrap conditional in curly braces => #{conditional_part}"
494
+ is_wrapped = conditional_part.start_with?("{") && conditional_part.end_with?("}")
495
+ raise RuntimeError.new no_curlies_msg unless is_wrapped
496
+
497
+ conditional_stmt = conditional_part[1..-2].strip
498
+ log.info(ere){ "Conditional Stmt => #{conditional_stmt}" }
499
+ conditional_val = evaluate( @@eval_prefix + conditional_stmt )
500
+ is_boolean = [true, false].include? conditional_val
501
+
502
+ boolean_msg = "=> #{conditional_stmt} <= evaluated to [#{conditional_val}] not boolean."
503
+ raise RuntimeError.new boolean_msg unless is_boolean
504
+
505
+ return false if is_if && conditional_val
506
+ return true if is_if && !conditional_val
507
+
508
+ return true if is_unless && conditional_val
509
+ return false if is_unless && !conditional_val
510
+
511
+ raise RuntimeError.new "Unreachable if[#{is_if}] unless[#{is_unless}] => #{conditional_val}"
512
+
513
+ end
514
+
515
+
516
+ #--
517
+ #-- Return the symbolic representation of the
518
+ #-- parameter key. Periods are replaced with
519
+ #-- underscores (as per the fact convention)
520
+ #-- before conversion to a symbol.
521
+ #--
522
+ #-- Nil is not handled.
523
+ #-- String is stripped beforehand just in case.
524
+ #--
525
+ def symbol from_string
526
+
527
+ return from_string.strip.gsub(".", "_").to_sym
528
+
529
+ end
530
+
531
+
532
+ #--
533
+ #-- Return the (key access) symbol that represents the
534
+ #-- plugin id plus a string given in the parameter.
535
+ #--
536
+ #-- ---------
537
+ #-- Example
538
+ #-- ---------
539
+ #--
540
+ #-- Plugin Id => ide.hub
541
+ #-- Append Str => host
542
+ #--
543
+ #-- equals
544
+ #--
545
+ #-- Key String => ide.hub.host
546
+ #-- Key Symbol => ide_hub_host
547
+ #--
548
+ #--
549
+ #-- So the symbol :ide_hub_host is returned.
550
+ #--
551
+ def plugin_symbol append_string
552
+
553
+ key_string = @i[:plugin] + "." + append_string.strip
554
+ return key_string.gsub(".", "_").to_sym
555
+
556
+ end
557
+
558
+
559
+ def get_key_symbol dirty_key_string
560
+
561
+ key_string = dirty_key_string.strip
562
+ split_string = "(unless)"
563
+ split_string = "(if)" if key_string.end_with? "(if)"
564
+ split_string = "(un)" if key_string.end_with? "(un)"
565
+
566
+ return key_string.split(split_string).first.gsub(".", "_").to_sym
567
+
568
+ end
569
+
570
+
571
+ def get_fact_value fact_value_string
572
+
573
+ is_conditional = fact_value_string.start_with?("{") && fact_value_string.include?( @@eval_prefix )
574
+ return fact_value_string unless is_conditional
575
+
576
+ return fact_value_string.rpartition( @@eval_prefix )[1..-1].join
577
+
578
+ end
579
+
580
+
581
+ def exists? fact_reference
582
+
583
+ log.info(ere) { "Does Fact Exist? => #{fact_reference}" }
584
+ return false if fact_reference.nil?
585
+ return false if fact_reference.strip.length == 0
586
+ return true if fact_reference.strip.length > 0
587
+
588
+ end
589
+
590
+
591
+ # --
592
+ # -- dot => period (full stop)
593
+ # -- Deliver a "." period character
594
+ # --
595
+ def dot
596
+ return "."
597
+ end
598
+
599
+
600
+ # --
601
+ # -- colon => full colon character
602
+ # -- Delivers a ":" colon character
603
+ # --
604
+ def colon
605
+ return ":"
606
+ end
607
+
608
+
609
+ def log_begin_workstation_identification the_filename
610
+
611
+ log.info(ere) { "- -" }
612
+ log.info(ere) { "# @@ @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ @@ #" }
613
+ log.info(ere) { "# -- ------------------------------------------------- -- #" }
614
+ log.info(ere) { "# -- [= BEGIN WORKSTATION IDENTIFICATION =] #{the_filename}" }
615
+ log.info(ere) { "# -- ------------------------------------------------- -- #" }
616
+ log.info(ere) { "# @@ @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ @@ #" }
617
+
618
+ end
619
+
620
+
621
+ def log_end_workstation_identification the_filename
622
+
623
+ log.info(ere) { "# @@ @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ @@ #" }
624
+ log.info(ere) { "# -- ------------------------------------------------- -- #" }
625
+ log.info(ere) { "# -- [= END WORKSTATION IDENTIFICATION =] #{the_filename}" }
626
+ log.info(ere) { "# -- ------------------------------------------------- -- #" }
627
+ log.info(ere) { "# @@ @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ @@ #" }
628
+ log.info(ere) { "- -" }
629
+ log.info(ere) { "- -" }
630
+ log.info(ere) { "- -" }
631
+
632
+ end
633
+
634
+
635
+ def log_begin the_filename
636
+
637
+ log.info(ere) { "- -" }
638
+ log.info(ere) { "# @@ @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ @@ #" }
639
+ log.info(ere) { "# -- ------------------------------------------------- -- #" }
640
+ log.info(ere) { "# -- [= BEGIN THE ASSIMILATION =] #{the_filename}" }
641
+ log.info(ere) { "# -- ------------------------------------------------- -- #" }
642
+ log.info(ere) { "# @@ @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ @@ #" }
643
+
644
+ end
645
+
646
+
647
+ def log_end the_filename
648
+
649
+ log.info(ere) { "# @@ @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ @@ #" }
650
+ log.info(ere) { "# -- ------------------------------------------------- -- #" }
651
+ log.info(ere) { "# -- [= END ASSIMILATION =] #{the_filename}" }
652
+ log.info(ere) { "# -- ------------------------------------------------- -- #" }
653
+ log.info(ere) { "# @@ @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ @@ #" }
654
+ log.info(ere) { "- -" }
655
+ log.info(ere) { "- -" }
656
+ log.info(ere) { "- -" }
657
+
658
+ end
659
+
660
+
661
+ end