opensecret 0.0.9925 → 0.0.9949

Sign up to get free protection for your applications and to get access to all the features.
Files changed (76) hide show
  1. checksums.yaml +4 -4
  2. data/README.md +656 -40
  3. data/lib/configs/README.md +58 -0
  4. data/lib/extension/file.rb +67 -0
  5. data/lib/extension/string.rb +10 -0
  6. data/lib/factbase/facts.opensecret.io.ini +1 -0
  7. data/lib/interprete.rb +334 -61
  8. data/lib/keytools/PRODUCE_RAND_SEQ_USING_DEV_URANDOM.txt +0 -0
  9. data/lib/keytools/kdf.api.rb +9 -15
  10. data/lib/keytools/kdf.bcrypt.rb +69 -19
  11. data/lib/keytools/kdf.pbkdf2.rb +112 -23
  12. data/lib/keytools/key.api.rb +146 -36
  13. data/lib/keytools/key.db.rb +94 -29
  14. data/lib/keytools/key.id.rb +1 -1
  15. data/lib/keytools/key.ident.rb +243 -0
  16. data/lib/keytools/key.local.rb +62 -68
  17. data/lib/keytools/key.pass.rb +2 -2
  18. data/lib/keytools/key.rb +2 -28
  19. data/lib/modules/{cryptology.md → README.md} +0 -0
  20. data/lib/session/fact.finder.rb +65 -428
  21. data/lib/session/time.stamp.rb +1 -28
  22. data/lib/usecase/cmd.rb +127 -54
  23. data/lib/usecase/config/README.md +57 -0
  24. data/lib/usecase/docker/README.md +146 -0
  25. data/lib/usecase/docker/docker.rb +49 -0
  26. data/lib/usecase/edit/README.md +43 -0
  27. data/lib/usecase/edit/delete.rb +46 -0
  28. data/lib/usecase/export.rb +40 -0
  29. data/lib/usecase/files/README.md +37 -0
  30. data/lib/usecase/files/eject.rb +56 -0
  31. data/lib/usecase/files/file_me.rb +78 -0
  32. data/lib/usecase/files/read.rb +169 -0
  33. data/lib/usecase/files/write.rb +89 -0
  34. data/lib/usecase/goto.rb +57 -0
  35. data/lib/usecase/id.rb +1 -1
  36. data/lib/usecase/import.rb +13 -30
  37. data/lib/usecase/init.rb +2 -17
  38. data/lib/usecase/jenkins/README.md +146 -0
  39. data/lib/usecase/jenkins/crazy_ruby_post_attempt.OLD +234 -0
  40. data/lib/usecase/jenkins/jenkins.rb +208 -0
  41. data/lib/usecase/login.rb +6 -5
  42. data/lib/usecase/logout.rb +1 -3
  43. data/lib/usecase/open.rb +11 -66
  44. data/lib/usecase/print.rb +40 -0
  45. data/lib/usecase/put.rb +34 -156
  46. data/lib/usecase/set.rb +2 -4
  47. data/lib/usecase/show.rb +138 -0
  48. data/lib/usecase/terraform/README.md +91 -0
  49. data/lib/usecase/terraform/terraform.rb +121 -0
  50. data/lib/usecase/token.rb +4 -80
  51. data/lib/usecase/update/README.md +55 -0
  52. data/lib/usecase/update/rename.rb +180 -0
  53. data/lib/usecase/use.rb +1 -3
  54. data/lib/usecase/verse.rb +20 -0
  55. data/lib/usecase/view.rb +71 -0
  56. data/lib/usecase/vpn/README.md +150 -0
  57. data/lib/usecase/vpn/vpn.ini +31 -0
  58. data/lib/usecase/vpn/vpn.rb +54 -0
  59. data/lib/version.rb +1 -1
  60. data/opensecret.gemspec +3 -4
  61. metadata +34 -35
  62. data/.travis.yml +0 -5
  63. data/CODE_OF_CONDUCT.md +0 -74
  64. data/LICENSE.txt +0 -21
  65. data/bin/ops +0 -20
  66. data/lib/keytools/binary.map.rb +0 -294
  67. data/lib/keytools/doc.conversion.to.ones.and.zeroes.ruby +0 -179
  68. data/lib/keytools/doc.rsa.radix.binary-mapping.ruby +0 -190
  69. data/lib/keytools/doc.star.schema.strategy.txt +0 -77
  70. data/lib/keytools/doc.using.pbkdf2.kdf.ruby +0 -95
  71. data/lib/keytools/doc.using.pbkdf2.pkcs.ruby +0 -266
  72. data/lib/keytools/key.mach.rb +0 -248
  73. data/lib/keytools/keydebug.txt +0 -295
  74. data/lib/modules/cryptology/open.bcrypt.rb +0 -170
  75. data/lib/usecase/read.rb +0 -89
  76. data/lib/usecase/safe.rb +0 -92
@@ -0,0 +1,58 @@
1
+
2
+ # Modifying Safe's Behaviour | 4 Configuration Scopes
3
+
4
+ Safe's behaviour can (by default) be modified in a manner that is scoped in 4 ways. Configuration directives can alter behaviour within
5
+
6
+ 1. a **book global** scope
7
+ 2. a **machine local** scope
8
+ 3. a **shell session** scope and
9
+ 4. a **machine global** scope
10
+
11
+ The scoping concept is similar to Git's --local and --global but it works in a different way.
12
+
13
+
14
+ ## 1. Book Global Scope
15
+
16
+ Directives issued against a safe book **"feel local"** but are global in that the behaviour persists on every machine that works with the book.
17
+
18
+ Git's --local is different because cloning the repository on another machine wipe's out the directives. With safe the directives continue to alter behaviour even when the book is cloned and/or used on another machine.
19
+
20
+
21
+ ## 2. Machine Local Scope
22
+
23
+ This is similar to Git's --global directive which affects all repositories owned by a user on a given machine.
24
+
25
+ Directives with a machine local scope **can influence the behaviour** of every Safe book one logs into on a machine. Move to another machine and the behaviour becomes unstuck.
26
+
27
+ == Configuration Directive Precedence
28
+
29
+ Note the sentence **can influence behaviour** as opposed to **will influence behaviour**.
30
+
31
+ If a directive with a book global scope says "Yes" and the same directive exists but says "No" with machine local scope the "Yes" wins out.
32
+
33
+ A book global directive overrides its machine local twin.
34
+
35
+
36
+ ## 3. Shell Session Scope
37
+
38
+ The self explanatory **shell session scoped** directives override their siblings be they book global or machine local.
39
+
40
+ Alas, their elevated privileges are countered by relatively short lifespans. Shell session directives only last until either a logout is issued or the shell session comes to an end.
41
+
42
+
43
+ ## 4. Default | Machine Global Scope
44
+
45
+ Did you notice only **one (1) user** is affected by directives with a machine local scope as long as it isn't overriden.
46
+
47
+ Directives with a **machine global scope** are the **default** and are set during an install or upgrade.
48
+
49
+ They can potentially affect **every user and every safe book**. Even though their longevity is undisputed, their precedence is the lowest when going head to head with their 3 siblings.
50
+
51
+ ## The Naked Eye
52
+
53
+ Directives with a book global scope **aren't visible to the naked eye**. They are encrypted within the master safe database and thus protected from prying eyes.
54
+
55
+ The other 3 directive types exist in plain text
56
+
57
+ - either where the gem is **installed** (machine global scope)
58
+ - or in the INI file in **.safe** off the user's home directory
@@ -3,6 +3,73 @@
3
3
  # Reopen the core ruby File class and add the below methods to it.
4
4
  class File
5
5
 
6
+ # Get the full filepath of a sister file that potentially lives
7
+ # in the same directory that the leaf class is executing from and
8
+ # has the same name as the leaf class but a different extension.
9
+ #
10
+ # == Usage
11
+ #
12
+ # If class OpenFoo:Bar extends class OpenFoo:Baz and we are looking
13
+ # for an INI file in the folder that OpenFoo:Bar lives in we can
14
+ # call this method within OpenFoo:Baz like this.
15
+ #
16
+ # ini_filepath = sister_filepath( "ini", :execute )
17
+ # # => /var/lib/gems/2.5.0/gems/fooey-0.2.99/lib/barry/bazzy/bar.ini
18
+ #
19
+ # == Common Implementation
20
+ #
21
+ # Object orientation scuppers the commonly used technique which
22
+ # derives the path from __FILE__
23
+ #
24
+ # class_directory = File.dirname( __FILE__ )
25
+ # leaf_class_name = self.class.name.split(":").last.downcase
26
+ # sister_filepath = File.join ( class_directory, "#{leaf_class_name}.#{extension}" )
27
+ #
28
+ # With object orientation - running the above code within the
29
+ # abstracted (parent) class would produce a resultant filepath
30
+ # based on the folder the parent class is in rather than the
31
+ # extended "concrete" class.
32
+ #
33
+ # == Value Proposition
34
+ #
35
+ # You can call this method from the parent (abstract) class and it
36
+ # will still correctly return the path to the potential sister file
37
+ # living in the directory that the leaf class sits in.
38
+ #
39
+ # Put differently - this extension method allows code executing in
40
+ # the parent class to correctly pinpoint a file in the directory of
41
+ # the leaf class be it in the same or a different folder.
42
+ #
43
+ # @param caller
44
+ # the calling class object usually passed in using <tt>self</tt>
45
+ #
46
+ # @param extension
47
+ # the extension of a sister file that carries the same simple
48
+ # (downcased) name of the leaf class of this method's caller.
49
+ #
50
+ # Omit the (segregating) period character when providing this
51
+ # extension parameter.
52
+ #
53
+ # @param method_symbol
54
+ # the method name in symbolic form of any method defined in
55
+ # the leaf class even if the method overrides one of the same
56
+ # name in the parent class.
57
+ #
58
+ # @return the filepath of a potential sister file living in the same
59
+ # directory as the class, bearing the same (downcased) name
60
+ # as the class with the specified extension.
61
+ def self.sister_filepath caller, extension, method_symbol
62
+
63
+ leaf_classname = caller.class.name.split(":").last.downcase
64
+ execute_method = caller.method( method_symbol )
65
+ leaf_classpath = execute_method.source_location.first
66
+ leaf_directory = File.dirname( leaf_classpath )
67
+ lower_filename = "#{leaf_classname}.#{extension}"
68
+ return File.join( leaf_directory, lower_filename )
69
+
70
+ end
71
+
72
+
6
73
  # This method adds (logging its own contents) behaviour to
7
74
  # the standard library {File} class. If this File points to
8
75
  # a directory - that folder's single level content files are
@@ -11,6 +11,16 @@
11
11
  # other parameter objects, like arrays and hashes).
12
12
  class String
13
13
 
14
+ ## ################################################
15
+ ## ################################################
16
+ ## ################################################
17
+ ## ################################################
18
+ ## https://www.di-mgt.com.au/cryptokeys.html
19
+ ## ################################################
20
+ ## ################################################
21
+ ## ################################################
22
+ ## ################################################
23
+ ## ################################################
14
24
 
15
25
  # Encrypt this string with the parameter symmetric encryption/decryption key
16
26
  # and then return the Base64 (block mode) encoded result.
@@ -27,6 +27,7 @@ session.file = ops.session.configuration.ini
27
27
  prompt.1 = Enter a Robust Password
28
28
  prompt.2 = Re-enter that Password
29
29
 
30
+
30
31
  [open]
31
32
 
32
33
  open.name = session
@@ -5,18 +5,21 @@ require "session/time.stamp"
5
5
  require "logging/gem.logging"
6
6
  require "session/require.gem"
7
7
 
8
+
8
9
  # Include the logger mixins so that every class can enjoy "import free"
9
10
  # logging through pointers to the (extended) log behaviour.
10
11
  include OpenLogger
11
12
 
13
+
12
14
  # This standard out sync command flushes text destined for STDOUT immediately,
13
15
  # without waiting either for a full cache or script completion.
14
16
  $stdout.sync = true
15
17
 
18
+
16
19
  # Recursively require all gems that are either in or under the directory
17
20
  # that this code is executing from. Only use this tool if your library is
18
21
  # relatively small but highly interconnected. In these instances it raises
19
- # productivity and reduces harassing "not found" exceptions.
22
+ # productivity and reduces pesky "not found" exceptions.
20
23
  OpenSession::RecursivelyRequire.now( __FILE__ )
21
24
 
22
25
 
@@ -28,18 +31,27 @@ OpenSession::RecursivelyRequire.now( __FILE__ )
28
31
  # - assert the type of each parameter
29
32
  # - ensure that the parameter values are in range
30
33
  # - delegate processing to the registered handlers
31
- #
34
+
32
35
  class Interprete < Thor
33
36
 
34
- log.info(x) {"opensecret session initiated at [#{OpenSession::Stamp.yyjjj_hhmm_sst}]." }
35
37
 
36
- # This class option allows every CLI call the option to include
37
- # a --debug boolean switch which will up the verbosity of the
38
- # content logged to the file .opensecret/opensecret.log
38
+ log.info(x) { "request to interact with a safe book has been received." }
39
+
40
+
41
+ # With this class option every (and especially the log) use case has
42
+ # the option of modifying its behaviour based on the presence and state
43
+ # of the --debug switch.
39
44
  class_option :debug, :type => :boolean
40
45
 
46
+ # The script class option is implemented in the parent {OpenSecret::UseCase}
47
+ # use case enabling behaviour alteration based on the presence and state of
48
+ # the --script flag.
49
+ class_option :script, :type => :boolean
50
+
51
+
52
+
41
53
  # Description of the init configuration call.
42
- desc "init <domain_name>, <base_path>", "initialize domain with keystore directory"
54
+ desc "init <book_name> <storage_dir>", "initialize the safe book on this device"
43
55
 
44
56
  # If confident that command history cannot be exploited to gain the
45
57
  # human password or if the agent running opensecret is itself a script,
@@ -51,7 +63,8 @@ class Interprete < Thor
51
63
  #
52
64
  # @param domain_name [String] the domain the software operates under
53
65
  # @param base_path [String] the path to the base operating directory
54
- def init domain_name, base_path = nil
66
+ def init( domain_name, base_path = nil )
67
+ log.info(x) { "initialize the safe book on this device." }
55
68
  init_uc = OpenSecret::Init.new
56
69
  init_uc.master_p4ss = options[:with] if options[:with]
57
70
  init_uc.domain_name = domain_name
@@ -60,8 +73,9 @@ class Interprete < Thor
60
73
  end
61
74
 
62
75
 
76
+
63
77
  # Description of the login use case command line call.
64
- desc "login <domain_name>", "Login to an application domain."
78
+ desc "login <book_name>", "login to the book before interacting with it"
65
79
 
66
80
  # If confident that command history cannot be exploited to gain the
67
81
  # human password or if the agent running opensecret is itself a script,
@@ -71,6 +85,7 @@ class Interprete < Thor
71
85
  # Login in order to securely interact with your data.
72
86
  # @param domain_name [String] the domain the software operates under
73
87
  def login( domain_name = nil )
88
+ log.info(x) { "[usecase] ~> login to the book before interacting with it." }
74
89
  login_uc = OpenSecret::Login.new
75
90
  login_uc.domain_name = domain_name unless domain_name.nil?
76
91
  login_uc.master_p4ss = options[:with] if options[:with]
@@ -79,72 +94,99 @@ class Interprete < Thor
79
94
 
80
95
 
81
96
 
97
+ # Description of the print use case command line call.
98
+ desc "print <key_name>", "print the key value at the opened chapter and verse"
99
+
100
+ # Print the value of the specified key belonging to a dictionary at
101
+ # the opened chapter and verse of the currently logged in book.
102
+ #
103
+ # @param key_name [String] the key whose value is to be printed
104
+ def print key_name
105
+ log.info(x) { "[usecase] ~> print the key value at the opened chapter and verse." }
106
+ print_uc = OpenSecret::Print.new
107
+ print_uc.key_name = key_name
108
+ print_uc.from_script = options[:script].nil? ? false : options[:script]
109
+ print_uc.flow_of_events
110
+ end
111
+
112
+
113
+
114
+ # Description of the verse use case command line call.
115
+ desc "verse", "print the verse name at the opened chapter and verse"
116
+
117
+ # Print the name of the verse at the opened chapter and verse location.
118
+ def verse
119
+ log.info(x) { "[usecase] ~> print the verse name at the opened chapter and verse." }
120
+ verse_uc = OpenSecret::Verse.new
121
+ verse_uc.from_script = options[:script].nil? ? false : options[:script]
122
+ verse_uc.flow_of_events
123
+ end
124
+
125
+
126
+
82
127
  # Description of the opensecret token use case.
83
- desc "token", "Produce an encrypted session token tied to the workstation and shell environment."
128
+ desc "token", "generate and print out an encrypted (shell bound) session token"
84
129
 
85
130
  # The<b>token</b> use cases prints out an encrypted session token tied
86
131
  # to the workstation and shell environment.
87
132
  def token
133
+ log.info(x) { "[usecase] ~> generate and print out an encrypted (shell bound) session token" }
88
134
  OpenSecret::Token.new.flow_of_events
89
135
  end
90
136
 
91
137
 
92
138
 
93
139
  # Description of the open use case command.
94
- desc "open ENVELOPE_PATH", "KEY_PATH open a key path within the specified envelope."
140
+ desc "open <chapter> <verse>", "open a chapter and verse to read from or write to"
95
141
 
96
142
  # Open up a conduit (path) to the place where we can issue read, create, update,
97
143
  # and destroy commands.
98
144
  #
99
- # @param env_path [String]
100
- # relative path to the obfuscated envelope
101
- # @param key_path [String]
102
- # path in envelope to the point of interest
103
- def open env_path, key_path
104
-
105
- open_uc = OpenSecret::Open.new
106
- open_uc.env_path = env_path
107
- open_uc.key_path = key_path
108
- open_uc.flow_of_events
109
-
110
- end
111
-
112
-
113
- # Description of the export use case command.
114
- desc "export OPEN_PATH", "OPEN_PATH to locked secrets to open for reading or stuffing."
115
-
116
- # If confident that command history cannot be exploited to gain the human password
117
- # or if the agent running opensecret is itself a script, the <tt>with</tt> option can
118
- # be used to convey the password.
119
- option :with
120
-
121
- # Export a secrets envelope at the specified outer path so that we can read, put
122
- # and discard secrets.
123
- #
124
- # This use case requires the human (agent) password unless the <tt>--no-human-password</tt>
125
- # flag was posted along with the <tt>init</tt> command.
145
+ # The allowed characters that makeup chapter and verse aside from alphanumerics are
126
146
  #
127
- # There are two ways to provide the password (for the <b><em>my/gadgets</em></b> group)
147
+ # - dollar signs
148
+ # - percent signs
149
+ # - ampersands
150
+ # - hyphens
151
+ # - underscores
152
+ # - plus signs
153
+ # - equal signs
154
+ # - @ signs
155
+ # - period characters and
156
+ # - question marks
128
157
  #
129
- # - <tt>opensecret export my/gadgets</tt> and respond to the password prompt (or)
130
- # - <tt>opensecret export my/gadgets --with="hUM4n-0pen$3cr3t"</tt>
158
+ # Notably whitespace including spaces and tabs are not allowed.
131
159
  #
132
- # If providing the password on the command line, one must be confident that the shell's
133
- # command history cannot be exploited to capture it.
160
+ # @param chapter [String]
161
+ # the chapter of the logged in book to open
134
162
  #
135
- # @param open_path [String] the path to the (previously) locked secrets in frozen storage.
136
- def export open_path
163
+ # @param verse [String]
164
+ # the verse of the logged in book and specified chapter to open
165
+ def open chapter, verse
166
+ log.info(x) { "[usecase] ~> open a chapter and verse to read from or write to." }
167
+ open_uc = OpenSecret::Open.new
168
+ open_uc.env_path = chapter
169
+ open_uc.key_path = verse
170
+ open_uc.flow_of_events
171
+ end
172
+
137
173
 
138
- export_uc = OpenSecret::Export.new
139
- export_uc.open_path = open_path
140
- export_uc.master_p4ss = options[:with] if options[:with]
141
- export_uc.flow_of_events
142
174
 
175
+ # Description of the export use case command.
176
+ desc "export", "exports the book or chapter or the mini dictionary at verse."
177
+
178
+ # Export the entire book if no chapter and verse is specified (achieved with a safe close),
179
+ # or the chapter if only the chapter is open (safe shut or safe open <<chapter>>, or the
180
+ # mini-dictionary at the verse if both chapter and verse are open.
181
+ def export
182
+ log.info(x) { "[usecase] ~> export book chapter content or dictionary at verse in JSON format." }
183
+ OpenSecret::Export.new.flow_of_events
143
184
  end
144
185
 
145
186
 
187
+
146
188
  # Description of the put secret command.
147
- desc "put <secret_id> <secret_value>", "put secret like login/username into opened context."
189
+ desc "put <key> <value>", "put key/value pair into dictionary at open chapter and verse"
148
190
 
149
191
  # Put a secret with an id like login/username and a value like joebloggs into the
150
192
  # context (eg work/laptop) that was opened with the open command.
@@ -152,38 +194,269 @@ class Interprete < Thor
152
194
  # @param secret_id [String] the id of the secret to put into the opened context
153
195
  # @param secret_value [String] the value of the secret to put into the opened context
154
196
  def put secret_id, secret_value
155
-
197
+ log.info(x) { "[usecase] ~> put key/value pair into dictionary at open chapter and verse." }
156
198
  put_uc = OpenSecret::Put.new
157
199
  put_uc.secret_id = secret_id
158
200
  put_uc.secret_value = secret_value
159
201
  put_uc.flow_of_events
202
+ end
160
203
 
204
+
205
+
206
+ # Description of the file command.
207
+ desc "file <file_key> <file_url>", "ingest a file into the safe from the filesystem (or S3, ssh, Google Drive)"
208
+
209
+ # The <b>file use case</b> pulls a read in from either an accessible readsystem
210
+ # or from a remote http, https, git, S3, GoogleDrive and/or ssh source.
211
+ #
212
+ # @param file_key [String] keyname representing the file that is being read in
213
+ # @param file_url [String] url of file to ingest and assimilate into the safe
214
+ def file file_key, file_url
215
+ log.info(x) { "[usecase] ~> file read against key [[ #{file_key} ]]" }
216
+ log.info(x) { "[usecase] ~> file read from url [[ #{file_url} ]]" }
217
+ file_uc = OpenSecret::FileMe.new
218
+ file_uc.file_key = file_key
219
+ file_uc.file_url = file_url
220
+ file_uc.flow_of_events
161
221
  end
162
222
 
163
223
 
164
- # Description of the read secret command.
165
- desc "read", "read and show secrets at the opened path."
166
224
 
167
- # Read the secrets at the opened path. These secrets
168
- # are simply written out to the shell console.
169
- def read
225
+ # Description of the eject command.
226
+ desc "eject <file_key>", "write out ingested file at chapter/verse with specified file key"
227
+
228
+ # The <b>eject use case</b> writes out a file that was previously ingested
229
+ # and coccooned inside the safe typically with the file command.
230
+ #
231
+ # @param file_key [String] the key that the file was ingested against
232
+ def eject file_key
233
+ log.info(x) { "[usecase] ~> eject file at chapter/verse against specified key." }
234
+ eject_uc = OpenSecret::Eject.new
235
+ eject_uc.file_key = file_key
236
+ eject_uc.flow_of_events
237
+ end
170
238
 
239
+
240
+
241
+ # Description of the delete command.
242
+ desc "delete <entity_id>", "delete a line (key/value pair), or a verse, chapter and even a book"
243
+
244
+ # The <b>delete use case</b> can delete a single line (key/value pair), or
245
+ # a verse, chapter and even a book
246
+ #
247
+ # @param entity_id [String] the ID of the entity to delete (line, verse, chapter or book)
248
+ def delete entity_id
249
+ log.info(x) { "[usecase] ~> delete a safe entity with a key id [#{entity_id}]." }
250
+ delete_uc = OpenSecret::DeleteMe.new
251
+ delete_uc.entity_id = entity_id
252
+ delete_uc.flow_of_events
253
+ end
254
+
255
+
256
+
257
+ # Description of the read command.
258
+ desc "read <file_url>", "read (reread) file either locally or via http, git or ssh"
259
+
260
+ # The <b>read use case</b> pulls a read in from either an accessible readsystem
261
+ # or from a remote http, https, git, S3, GoogleDrive and/or ssh source.
262
+ #
263
+ # This use case expects a @file_url parameter. The actions it takes are to
264
+ #
265
+ # - register @in.url to mirror @file_url
266
+ # - register @out.url to mirror @file_url
267
+ # - check the location of @file_url
268
+ # - if no file exists it humbly finishes up
269
+ #
270
+ # @param file_url [String] url of file to ingest and assimilate into the safe
271
+ def read file_url
272
+ log.info(x) { "[usecase] ~> read (reread) file from optional url [[ #{file_url} ]]" }
171
273
  read_uc = OpenSecret::Read.new
274
+ read_uc.file_url = file_url
172
275
  read_uc.flow_of_events
276
+ end
277
+
278
+
279
+
280
+ # Description of the write command.
281
+ desc "write <file_url>", "write out file at chapter/verse to (optional) file url"
173
282
 
283
+ # The <b>write use case</b> writes out a file that was previously ingested
284
+ # and coccooned inside the safe.
285
+ #
286
+ # @param file_url [String] optional file url marking where to write the file
287
+ def write( file_url = nil )
288
+ log.info(x) { "[usecase] ~> write out file at chapter/verse to (optional) file url." }
289
+ write_uc = OpenSecret::Write.new
290
+ write_uc.from_script = options[:script].nil? ? false : options[:script]
291
+ write_uc.file_url = file_url if file_url
292
+ write_uc.flow_of_events
174
293
  end
175
294
 
176
295
 
177
- # Description of the print identifier command.
178
- desc "id", "print multiple formats of the current timestamp."
179
296
 
180
- # Print the multiple formats of the current timestamp.
181
- def id
297
+ # Description of the show secret command.
298
+ desc "show", "show dictionary at the opened chapter and verse"
299
+
300
+ # Show the secrets at the opened path. These secrets
301
+ # are simply written out to the shell console.
302
+ def show
303
+ log.info(x) { "[usecase] ~> show dictionary at the opened chapter and verse." }
304
+ OpenSecret::Show.new.flow_of_events
305
+ end
306
+
307
+
308
+
309
+ # Description of the view command.
310
+ desc "view", "print list of chapter and verse combos to console"
311
+
312
+ # Display a bird's eye view of the domain's database including
313
+ # its envelopes, their keys and imported objects such as files.
314
+ def view
315
+ log.info(x) { "[usecase] ~> print list of chapter and verse combos to console." }
316
+ view_uc = OpenSecret::View.new
317
+ view_uc.flow_of_events
318
+ end
319
+
320
+
321
+
322
+ # Description of the goto use case command.
323
+ desc "goto <index>", "shortcut that opens chapter and verse at specified index"
324
+
325
+ # Goto is a shortcut (or alias even) for the open command that takes an integer
326
+ # index that effectively specifies which <envelope> and <key> to open.
327
+ #
328
+ # @param index [Number]
329
+ # the integer index chosen from the list procured by the view command.
330
+ def goto index
331
+ log.info(x) { "[usecase] ~> opens the chapter and verse at index [#{index}]." }
332
+ goto_uc = OpenSecret::Goto.new
333
+ goto_uc.index = index
334
+ goto_uc.flow_of_events
335
+
336
+ end
182
337
 
338
+
339
+
340
+ # Description of the terraform integration use case command.
341
+ desc "terraform <command>", "runs terraform after exporting IAM credentials at opened location"
342
+
343
+ # This terraform use case exports the AWS IAM user access key, secret key and region key
344
+ # into (very safe) environment variables and then runs terraform plan, apply or destroy.
345
+ #
346
+ # This is both ultra secure and extremely convenient because the credentials do not leave
347
+ # the safe and exist within (environment variable) memory only for the duration of the
348
+ # terraform command.
349
+ #
350
+ # It is safe because you do not need to expose your AWS credentials in plain text.
351
+ # It is convenient because switching IAM users and AWS regions is as easy as typing the now
352
+ # ubiquitous safe open command.
353
+ #
354
+ # safe open <<chapter>> <<verse>>
355
+ #
356
+ # @param command [String]
357
+ # the terraform command to run which is currently limited to plan, apply and destroy.
358
+ # This parameter is optional and if nothing is given then "apply" is assumed.
359
+ def terraform( command = nil )
360
+ log.info(x) { "[usecase] ~> will export IAM credentials then invoke $ terraform #{command}" }
361
+ terraform_uc = OpenSecret::Terraform.new
362
+ terraform_uc.command = command if command
363
+ terraform_uc.flow_of_events
364
+ end
365
+
366
+
367
+
368
+ # Description of the jenkins integration use case command.
369
+ desc "jenkins <<command>> <<what>> <<where>>", "sends credentials to the Jenkins 2 CI service."
370
+
371
+ # This Jenkins use case injects for example the AWS IAM user access key, secret key and region key
372
+ # into a running Jenkins CI (Continuous Integration) service at the specified (url) location.
373
+ #
374
+ # safe jenkins post aws http://localhost:8080
375
+ #
376
+ # @param command [String]
377
+ #
378
+ # the action to be taken which is currently limited to be [post].
379
+ #
380
+ # @param service [String]
381
+ #
382
+ # Which service do the credentials being posted originate from? The crrent list includes
383
+ #
384
+ # - aws ( the 3 IAM user credentials )
385
+ # - docker ( the username / password of docker repository )
386
+ # - git ( the username/password of Git repository )
387
+ # - rubygems ( the username / password of RubyGems package manager account )
388
+ #
389
+ # @param url [String]
390
+ #
391
+ # the full url of the jenkins service for example http://localhost:8080
392
+ # which includes the scheme (http|https) the hostname or ip address and
393
+ # the port jenkins is listening on (if not the default 80 or 443).
394
+ #
395
+ def jenkins( command, service, url )
396
+
397
+ log.info(x) { "[usecase] ~> request to #{command} #{service} credentials to Jenkins at #{url}" }
398
+ jenkins_uc = OpenSecret::Jenkins.new
399
+
400
+ jenkins_uc.command = command if command
401
+ jenkins_uc.service = service if service
402
+ jenkins_uc.url = url if url
403
+
404
+ jenkins_uc.flow_of_events
405
+
406
+ end
407
+
408
+
409
+
410
+ # Description of the docker repository integration use case command.
411
+ desc "docker <<command>>", "logs into or out of the dockerhub repository."
412
+
413
+ # This docker use case ....
414
+ #
415
+ # safe docker login
416
+ # safe docker logout
417
+ #
418
+ # @param command [String]
419
+ # the action to be taken which is currently limited to either
420
+ # login or logout
421
+ def docker( command = "login" )
422
+
423
+ log.info(x) { "[usecase] ~> request to #{command} into or out of a docker repository." }
424
+ docker_uc = OpenSecret::Docker.new
425
+ docker_uc.command = command
426
+ docker_uc.flow_of_events
427
+
428
+ end
429
+
430
+
431
+
432
+ # Description of the vpn use case command.
433
+ desc "vpn <command>", "runs vpn command typically safe vpn up or safe vpn down"
434
+
435
+ # This VPN use case connects to the VPN whose specifics are recorded within the vpn.ini
436
+ # factfile living in the same directory as the vpn.rb usecase class.
437
+ #
438
+ # @param command [String]
439
+ # the vpn command to run which is currently limited to up or down
440
+ # This parameter is optional and if nothing is given then "up" is assumed.
441
+ def vpn( command = nil )
442
+ log.info(x) { "[usecase] ~> VPN connection command #{command} has been issued." }
443
+ vpn_uc = OpenSecret::Vpn.new
444
+ vpn_uc.command = command if command
445
+ vpn_uc.flow_of_events
446
+ end
447
+
448
+
449
+
450
+ # Description of the identifier command.
451
+ desc "id", "prints out the current timestamp identifiers"
452
+
453
+ # Put out the multiple formats of the current timestamp.
454
+ def id
455
+ log.info(x) { "[usecase] ~> prints out the current timestamp identifiers." }
183
456
  id_uc = OpenSecret::Id.new
184
457
  id_uc.flow_of_events
185
-
186
458
  end
187
459
 
188
460
 
461
+
189
462
  end