rapid-vaults 1.1.2 → 1.2.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/README.md +16 -6
- data/lib/rapid-vaults/api.rb +4 -5
- data/lib/rapid-vaults/bindings/puppet_gpg_decrypt.rb +1 -1
- data/lib/rapid-vaults/bindings/puppet_gpg_encrypt.rb +1 -1
- data/lib/rapid-vaults/bindings/puppet_ssl_decrypt.rb +7 -6
- data/lib/rapid-vaults/bindings/puppet_ssl_encrypt.rb +10 -8
- data/lib/rapid-vaults/cli.rb +4 -6
- data/lib/rapid-vaults/decrypt.rb +10 -5
- data/lib/rapid-vaults/encrypt.rb +13 -7
- data/lib/rapid-vaults/generate.rb +4 -3
- data/lib/rapid-vaults/grpc.rb +77 -0
- data/lib/{rapid-vaults.rb → rapid_vaults.rb} +5 -7
- data/spec/rapid-vaults/decrypt_spec.rb +20 -5
- data/spec/rapid-vaults/encrypt_spec.rb +16 -4
- data/spec/rapid-vaults/generate_spec.rb +1 -1
- data/spec/rapid-vaults/grpc_spec.rb +42 -0
- data/spec/{rapid-vaults_spec.rb → rapid_vaults_spec.rb} +13 -7
- data/spec/spec_helper.rb +1 -1
- data/spec/system/system_spec.rb +9 -9
- metadata +71 -33
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: eab7b432d2da9ded261c422b220051585469fdd3c93dad84b2e4b9c8b272f20a
|
4
|
+
data.tar.gz: ce1aa65551bea26216d87c1137cb076b75b501bac785380ae78dd3161b5b0d7a
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 59f7a29f22852e58074bd85823028b178f23117c7adb3ce491a18271263f4cf92cc8e201e8bd31949a3d0b106879802755d4bd393909a57b21f295b6123585b6
|
7
|
+
data.tar.gz: 6048157efbe27b351b50b102fc2dcc19604de178d6282b45098beb3d51669ff4b833ae06051a727c5768a7b933b04c3cb6850bb9644e5d6b236df95117a081ad
|
data/README.md
CHANGED
@@ -1,13 +1,15 @@
|
|
1
1
|
# Rapid Vaults
|
2
2
|
[![Build Status](https://travis-ci.org/mschuchard/rapid-vaults.svg?branch=master)](https://travis-ci.org/mschuchard/rapid-vaults)
|
3
|
+
[![CircleCI](https://circleci.com/gh/mschuchard/rapid-vaults.svg?style=svg)](https://circleci.com/gh/mschuchard/rapid-vaults)
|
3
4
|
|
4
5
|
- [Description](#description)
|
5
6
|
- [Usage](#usage)
|
6
7
|
- [CLI](#cli)
|
7
8
|
- [API](#api)
|
9
|
+
- [gRPC](#grpc)
|
10
|
+
- [Docker](#docker)
|
8
11
|
- [Ansible](#ansible)
|
9
12
|
- [Puppet](#puppet)
|
10
|
-
- [Hiera](#hiera)
|
11
13
|
- [Chef](#chef)
|
12
14
|
- [Contributing](#contributing)
|
13
15
|
|
@@ -21,7 +23,7 @@ Ansible-Vault is very similar to Rapid Vaults. Both are streamlined and easy to
|
|
21
23
|
|
22
24
|
### Non-Comparative Software
|
23
25
|
|
24
|
-
Rapid Vaults is not similar to tools like RbNaCl or Hashicorp's Vault. RbNaCl offers advanced encryption techniques by providing bindings to libsodium. Rapid Vaults relies upon AES-256-GCM (OpenSSL) or GPG's algorithms (RSA, SHA-512, etc.). Hashicorp's Vault is Enterprise level software with many powerful features and conveniences. Rapid Vaults is a lightweight and narrowly focused tool.
|
26
|
+
Rapid Vaults is not similar to tools like RbNaCl or Hashicorp's Vault. RbNaCl offers advanced encryption techniques by providing bindings to libsodium. Rapid Vaults relies upon AES-256-GCM (OpenSSL) or GPG's algorithms (RSA, SHA-512, etc.). Hashicorp's Vault is Enterprise level software with many powerful features and conveniences. Rapid Vaults is a lightweight and narrowly focused tool. However, Rapid Vaults can be considered algorithmically very similar to Vault's Transit secret engine.
|
25
27
|
|
26
28
|
## Usage
|
27
29
|
|
@@ -50,11 +52,11 @@ usage: rapid-vaults [options] file
|
|
50
52
|
|
51
53
|
#### Encrypt File with SSL
|
52
54
|
|
53
|
-
`rapid-vaults -e -k
|
55
|
+
`rapid-vaults -e -k key.txt -n nonce.txt -p secret -o /output/dir unencrypted.txt`
|
54
56
|
|
55
57
|
#### Decrypt a File with SSL
|
56
58
|
|
57
|
-
`rapid-vaults -d -k
|
59
|
+
`rapid-vaults -d -k key.txt -n nonce.txt -t tag.txt -p secret -o /output/dir encrypted.txt`
|
58
60
|
|
59
61
|
#### Generate Keys with GPG
|
60
62
|
This is the only situation where a `--gpgparams` flag and argument is required or utilized. The file provided as the argument should look like the following:
|
@@ -112,7 +114,7 @@ require 'rapid-vaults'
|
|
112
114
|
options = {}
|
113
115
|
options[:action] = :encrypt
|
114
116
|
options[:file] = '/path/to/data.txt'
|
115
|
-
options[:key] = '/path/to/
|
117
|
+
options[:key] = '/path/to/key.txt'
|
116
118
|
options[:nonce] = '/path/to/nonce.txt'
|
117
119
|
options[:pw] = File.read('/path/to/password.txt') # optional
|
118
120
|
encrypted_contents, tag = RapidVaults::API.main(options)
|
@@ -126,7 +128,7 @@ require 'rapid-vaults'
|
|
126
128
|
options = {}
|
127
129
|
options[:action] = :decrypt
|
128
130
|
options[:file] = '/path/to/encrypted_data.txt'
|
129
|
-
options[:key] = '/path/to/
|
131
|
+
options[:key] = '/path/to/key.txt'
|
130
132
|
options[:nonce] = '/path/to/nonce.txt'
|
131
133
|
options[:tag] = '/path/to/tag.txt'
|
132
134
|
options[:pw] = File.read('/path/to/password.txt') # optional
|
@@ -192,6 +194,14 @@ options[:pw] = File.read('/path/to/password.txt')
|
|
192
194
|
decrypted_contents = RapidVaults::API.main(options)
|
193
195
|
```
|
194
196
|
|
197
|
+
### Docker
|
198
|
+
|
199
|
+
A supported [Docker image](https://hub.docker.com/r/matthewschuchard/rapid-vaults) of Rapid-Vaults is now available from the public Docker Hub registry. Please consult the repository documentation for further usage information.
|
200
|
+
|
201
|
+
### gRPC
|
202
|
+
|
203
|
+
forthcoming
|
204
|
+
|
195
205
|
### Ansible
|
196
206
|
|
197
207
|
forthcoming
|
data/lib/rapid-vaults/api.rb
CHANGED
@@ -1,17 +1,16 @@
|
|
1
|
-
require_relative '../
|
1
|
+
require_relative '../rapid_vaults'
|
2
2
|
|
3
3
|
# provides an application programming interface to interact with rapid vaults
|
4
4
|
class RapidVaults::API
|
5
5
|
# lightweight api
|
6
6
|
def self.main(settings)
|
7
|
-
# parse settings for api and run RapidVaults with specified settings
|
7
|
+
# parse pass-by-value settings for api and run RapidVaults with specified settings
|
8
8
|
RapidVaults.new.main(parse(settings))
|
9
9
|
end
|
10
10
|
|
11
|
-
# parse api options
|
11
|
+
# parse api options; this is mostly here for unit testing
|
12
12
|
def self.parse(settings)
|
13
13
|
# establish settings for api and denote using api
|
14
|
-
settings
|
15
|
-
settings
|
14
|
+
settings.merge({ ui: :api })
|
16
15
|
end
|
17
16
|
end
|
@@ -1,5 +1,5 @@
|
|
1
1
|
# mymodule/lib/puppet/functions/gpg_decrypt.rb
|
2
|
-
Puppet::Functions.create_function(:
|
2
|
+
Puppet::Functions.create_function(:gpg_decrypt) do
|
3
3
|
# Decrypts a file with GnuPG.
|
4
4
|
# @param [String] file The file to decrypt.
|
5
5
|
# @param [String] gpghome The path to the GnuPG home directory containing the credentials.
|
@@ -1,5 +1,5 @@
|
|
1
1
|
# mymodule/lib/puppet/functions/gpg_encrypt.rb
|
2
|
-
Puppet::Functions.create_function(:
|
2
|
+
Puppet::Functions.create_function(:gpg_encrypt) do
|
3
3
|
# Encrypts a file with GnuPG.
|
4
4
|
# @param [String] file The file to encrypt.
|
5
5
|
# @param [String] gpghome The path to the GnuPG home directory containing the credentials.
|
@@ -1,5 +1,5 @@
|
|
1
1
|
# mymodule/lib/puppet/functions/ssl_decrypt.rb
|
2
|
-
Puppet::Functions.create_function(:
|
2
|
+
Puppet::Functions.create_function(:ssl_decrypt) do
|
3
3
|
# Decrypts a file with OpenSSL.
|
4
4
|
# @param [String] file The file to decrypt.
|
5
5
|
# @param [String] key The key file to use for decryption.
|
@@ -25,10 +25,11 @@ Puppet::Functions.create_function(:'ssl_decrypt') do
|
|
25
25
|
raise 'Rapid Vaults is required to be installed on the puppet master to use this custom function!'
|
26
26
|
end
|
27
27
|
|
28
|
-
|
29
|
-
|
30
|
-
|
31
|
-
|
32
|
-
|
28
|
+
# initialize settings
|
29
|
+
settings = { action: :decrypt, file: file, key: key, nonce: nonce, tag: tag }
|
30
|
+
# update settings with password if input
|
31
|
+
settings[pw: File.read(password_file)] unless password_file.nil?
|
32
|
+
|
33
|
+
RapidVaults::API.main(settings)
|
33
34
|
end
|
34
35
|
end
|
@@ -1,5 +1,5 @@
|
|
1
1
|
# mymodule/lib/puppet/functions/ssl_encrypt.rb
|
2
|
-
Puppet::Functions.create_function(:
|
2
|
+
Puppet::Functions.create_function(:ssl_encrypt) do
|
3
3
|
# Encrypts a file with OpenSSL.
|
4
4
|
# @param [String] file The file to encrypt.
|
5
5
|
# @param [String] key The key file to use for encryption.
|
@@ -23,12 +23,14 @@ Puppet::Functions.create_function(:'ssl_encrypt') do
|
|
23
23
|
raise 'Rapid Vaults is required to be installed on the puppet master to use this custom function!'
|
24
24
|
end
|
25
25
|
|
26
|
-
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
|
31
|
-
|
32
|
-
|
26
|
+
# initialize settings and return
|
27
|
+
settings = { action: :encrypt, file: file, key: key, nonce: nonce }
|
28
|
+
return_hash = {}
|
29
|
+
# update settings with password if input
|
30
|
+
settings[pw: File.read(password_file)] unless password_file.nil?
|
31
|
+
|
32
|
+
return_hash[:encrypted_contents], return_hash[:tag] = RapidVaults::API.main(settings)
|
33
|
+
|
34
|
+
return_hash
|
33
35
|
end
|
34
36
|
end
|
data/lib/rapid-vaults/cli.rb
CHANGED
@@ -1,4 +1,4 @@
|
|
1
|
-
require_relative '../
|
1
|
+
require_relative '../rapid_vaults'
|
2
2
|
|
3
3
|
# provides a command line interface to interact with rapid vaults
|
4
4
|
class RapidVaults::CLI
|
@@ -22,10 +22,8 @@ class RapidVaults::CLI
|
|
22
22
|
# show help message if no args specified
|
23
23
|
args = %w[-h] if args.empty?
|
24
24
|
|
25
|
-
# init settings
|
26
|
-
settings = {}
|
27
|
-
# specify cli being used
|
28
|
-
settings[:ui] = :cli
|
25
|
+
# init settings with cli setting
|
26
|
+
settings = { ui: :cli }
|
29
27
|
|
30
28
|
opt_parser = OptionParser.new do |opts|
|
31
29
|
# usage
|
@@ -33,7 +31,7 @@ class RapidVaults::CLI
|
|
33
31
|
|
34
32
|
# base options
|
35
33
|
opts.on('--version', 'Display the current version.') do
|
36
|
-
puts 'rapid-vaults 1.
|
34
|
+
puts 'rapid-vaults 1.2.0'
|
37
35
|
exit 0
|
38
36
|
end
|
39
37
|
|
data/lib/rapid-vaults/decrypt.rb
CHANGED
@@ -4,7 +4,10 @@ class Decrypt
|
|
4
4
|
def self.openssl(settings)
|
5
5
|
require 'openssl'
|
6
6
|
|
7
|
-
#
|
7
|
+
# validate key, nonce, encrypted, and tag
|
8
|
+
raise 'The key is not a valid 32 byte key.' unless settings[:key].bytesize == 32
|
9
|
+
raise 'The nonce is not a valid 12 byte nonce.' unless settings[:nonce].bytesize == 12
|
10
|
+
raise 'The encrypted data is not a valid multiple of 9 bytes.' unless (settings[:file].bytesize % 9).zero?
|
8
11
|
raise 'Tag is not 16 bytes.' unless settings[:tag].bytesize == 16
|
9
12
|
|
10
13
|
# setup the decryption parameters
|
@@ -15,11 +18,12 @@ class Decrypt
|
|
15
18
|
decipher.auth_data = settings.key?(:pw) ? settings[:pw] : ''
|
16
19
|
|
17
20
|
# output the decryption
|
18
|
-
|
21
|
+
case settings[:ui]
|
22
|
+
when :cli
|
19
23
|
# output to file
|
20
24
|
File.write("#{settings[:outdir]}decrypted.txt", decipher.update(settings[:file]) + decipher.final)
|
21
25
|
puts "Your decrypted.txt has been written out to #{settings[:outdir]}."
|
22
|
-
|
26
|
+
when :api
|
23
27
|
# output to string
|
24
28
|
decipher.update(settings[:file]) + decipher.final
|
25
29
|
end
|
@@ -37,11 +41,12 @@ class Decrypt
|
|
37
41
|
crypto = GPGME::Crypto.new(armor: true, pinentry_mode: GPGME::PINENTRY_MODE_LOOPBACK)
|
38
42
|
|
39
43
|
# output the decryption
|
40
|
-
|
44
|
+
case settings[:ui]
|
45
|
+
when :cli
|
41
46
|
# output to file
|
42
47
|
File.write("#{settings[:outdir]}decrypted.txt", crypto.decrypt(encrypted, password: settings[:pw]).read)
|
43
48
|
puts "Your decrypted.txt has been written out to #{settings[:outdir]}."
|
44
|
-
|
49
|
+
when :api
|
45
50
|
# output to string
|
46
51
|
crypto.decrypt(encrypted, password: settings[:pw]).read
|
47
52
|
end
|
data/lib/rapid-vaults/encrypt.rb
CHANGED
@@ -4,6 +4,10 @@ class Encrypt
|
|
4
4
|
def self.openssl(settings)
|
5
5
|
require 'openssl'
|
6
6
|
|
7
|
+
# validate key and nonce
|
8
|
+
raise 'The key is not a valid 32 byte key.' unless settings[:key].bytesize == 32
|
9
|
+
raise 'The nonce is not a valid 12 byte nonce.' unless settings[:nonce].bytesize == 12
|
10
|
+
|
7
11
|
# setup the encryption parameters
|
8
12
|
cipher = OpenSSL::Cipher.new('aes-256-gcm').encrypt
|
9
13
|
cipher.key = settings[:key]
|
@@ -11,13 +15,14 @@ class Encrypt
|
|
11
15
|
cipher.auth_data = settings.key?(:pw) ? settings[:pw] : ''
|
12
16
|
|
13
17
|
# output the encryption and associated tag
|
14
|
-
|
18
|
+
case settings[:ui]
|
19
|
+
when :cli
|
15
20
|
# output to file
|
16
21
|
File.write("#{settings[:outdir]}encrypted.txt", cipher.update(settings[:file]) + cipher.final)
|
17
22
|
File.write("#{settings[:outdir]}tag.txt", cipher.auth_tag)
|
18
23
|
puts "Your encrypted.txt and associated tag.txt for this encryption have been generated in #{settings[:outdir]}."
|
19
|
-
|
20
|
-
#
|
24
|
+
when :api
|
25
|
+
# return as array
|
21
26
|
[cipher.update(settings[:file]) + cipher.final, cipher.auth_tag]
|
22
27
|
end
|
23
28
|
end
|
@@ -33,12 +38,13 @@ class Encrypt
|
|
33
38
|
crypto = GPGME::Crypto.new(armor: true, pinentry_mode: GPGME::PINENTRY_MODE_LOOPBACK)
|
34
39
|
|
35
40
|
# output the encryption and associated tag
|
36
|
-
|
41
|
+
case settings[:ui]
|
42
|
+
when :cli
|
37
43
|
# output to file
|
38
44
|
File.write("#{settings[:outdir]}encrypted.txt", crypto.encrypt(settings[:file], symmetric: true, password: settings[:pw]).read)
|
39
|
-
puts "Your encrypted.txt for this encryption
|
40
|
-
|
41
|
-
#
|
45
|
+
puts "Your encrypted.txt for this encryption has been generated in #{settings[:outdir]}."
|
46
|
+
when :api
|
47
|
+
# return as string
|
42
48
|
crypto.encrypt(settings[:file], symmetric: true, password: settings[:pw]).read
|
43
49
|
end
|
44
50
|
end
|
@@ -7,13 +7,14 @@ class Generate
|
|
7
7
|
# setup parameters
|
8
8
|
cipher = OpenSSL::Cipher.new('aes-256-gcm').encrypt
|
9
9
|
|
10
|
-
|
10
|
+
case settings[:ui]
|
11
|
+
when :cli
|
11
12
|
# output to file
|
12
13
|
File.write("#{settings[:outdir]}key.txt", cipher.random_key)
|
13
14
|
File.write("#{settings[:outdir]}nonce.txt", cipher.random_iv)
|
14
15
|
puts "Your key.txt and nonce.txt have been generated in #{settings[:outdir]}."
|
15
|
-
|
16
|
-
#
|
16
|
+
when :api
|
17
|
+
# return as array
|
17
18
|
[cipher.random_key, cipher.random_iv]
|
18
19
|
end
|
19
20
|
end
|
@@ -0,0 +1,77 @@
|
|
1
|
+
require_relative '../rapid_vaults'
|
2
|
+
require_relative 'bindings/rapid_vaults_services_pb'
|
3
|
+
|
4
|
+
# provides a grpc server
|
5
|
+
class RapidVaults::GRPC < Rapidvaults::RapidVaults::Service
|
6
|
+
# start the server
|
7
|
+
def server(addr = '0.0.0.0:8080')
|
8
|
+
server = GRPC::RpcServer.new
|
9
|
+
server.add_http2_port(addr, :this_port_is_insecure)
|
10
|
+
server.handle(RapidVaults.new)
|
11
|
+
server.run_till_terminated
|
12
|
+
end
|
13
|
+
|
14
|
+
# grpc api for generate openssl
|
15
|
+
def ssl_generate(geninputs, _call)
|
16
|
+
settings = geninputs.to_hash
|
17
|
+
settings_process(settings)
|
18
|
+
Generate.openssl(settings)
|
19
|
+
end
|
20
|
+
|
21
|
+
# grpc api for generate gpg
|
22
|
+
def gpg_generate(geninputs, _call)
|
23
|
+
settings = geninputs.to_hash
|
24
|
+
settings_process(settings)
|
25
|
+
Generate.gpgme(settings)
|
26
|
+
end
|
27
|
+
|
28
|
+
# grpc api for encrypt ssl
|
29
|
+
def ssl_encrypt(unencrypted, _call)
|
30
|
+
settings = {}
|
31
|
+
settings[:file] = unencrypted.text
|
32
|
+
settings[:key] = unencrypted.key
|
33
|
+
settings[:nonce] = unencrypted.nonce
|
34
|
+
settings[:pw] = unencrypted.password
|
35
|
+
settings_process(settings)
|
36
|
+
Encrypt.openssl(settings)
|
37
|
+
end
|
38
|
+
|
39
|
+
# grpc api for encrypt gpg
|
40
|
+
def gpg_encrypt(unencrypted, _call)
|
41
|
+
settings = {}
|
42
|
+
settings[:file] = unencrypted.text
|
43
|
+
settings[:pw] = unencrypted.password
|
44
|
+
settings_process(settings)
|
45
|
+
Encrypt.gpgme(settings)
|
46
|
+
end
|
47
|
+
|
48
|
+
# grpc api for ssl decrypt
|
49
|
+
def ssl_decrypt(undecrypted, _call)
|
50
|
+
settings = {}
|
51
|
+
settings[:file] = undecrypted.text
|
52
|
+
settings[:key] = undecrypted.key
|
53
|
+
settings[:nonce] = undecrypted.nonce
|
54
|
+
settings[:tag] = undecrypted.tag
|
55
|
+
settings[:pw] = undecrypted.password
|
56
|
+
settings_process(settings)
|
57
|
+
Decrypt.openssl(settings)
|
58
|
+
end
|
59
|
+
|
60
|
+
# grpc api for gpg decrypt
|
61
|
+
def gpg_decrypt(undecrypted, _call)
|
62
|
+
settings = {}
|
63
|
+
settings[:file] = undecrypted.text
|
64
|
+
settings[:pw] = undecrypted.password
|
65
|
+
settings_process(settings)
|
66
|
+
Decrypt.gpgme(settings)
|
67
|
+
end
|
68
|
+
|
69
|
+
private
|
70
|
+
|
71
|
+
# helper method
|
72
|
+
def settings_process(settings)
|
73
|
+
settings[:ui] = :api
|
74
|
+
RapidVaults.process(settings)
|
75
|
+
settings
|
76
|
+
end
|
77
|
+
end
|
@@ -7,7 +7,7 @@ require_relative 'rapid-vaults/binding'
|
|
7
7
|
class RapidVaults
|
8
8
|
# main runner for software
|
9
9
|
def main(settings)
|
10
|
-
# process settings
|
10
|
+
# process settings via pass-by-reference
|
11
11
|
self.class.process(settings)
|
12
12
|
|
13
13
|
# execute desired action and algorithm via dynamic call
|
@@ -50,7 +50,7 @@ class RapidVaults
|
|
50
50
|
end
|
51
51
|
|
52
52
|
# lambda for input processing
|
53
|
-
process_input = ->(input) { File.
|
53
|
+
process_input = ->(input) { File.readable?(settings[input]) ? settings[input] = File.read(settings[input]) : (raise "Input file '#{settings[input]}' for argument '#{input}' is not an existing readable file.") }
|
54
54
|
|
55
55
|
# check inputs and read in files
|
56
56
|
raise 'Password must be a string.' if settings.key?(:pw) && !settings[:pw].is_a?(String)
|
@@ -66,14 +66,12 @@ class RapidVaults
|
|
66
66
|
case settings[:action]
|
67
67
|
when :generate
|
68
68
|
raise 'GPG params file argument required for generation.' unless settings.key?(:gpgparams)
|
69
|
-
return
|
70
69
|
when :decrypt, :encrypt
|
70
|
+
# check inputs and read in files
|
71
71
|
raise 'File and password arguments required for encryption or decryption.' unless settings.key?(:file) && settings.key?(:pw)
|
72
|
+
raise 'Password must be a string.' unless settings[:pw].is_a?(String)
|
73
|
+
settings[:file] = File.readable?(settings[:file]) ? File.read(settings[:file]) : (raise "Input file '#{settings[:file]}' for argument 'file' is not an existing readable file.")
|
72
74
|
else raise 'Action must be one of generate, encrypt, or decrypt.'
|
73
75
|
end
|
74
|
-
|
75
|
-
# check inputs and read in files
|
76
|
-
raise 'Password must be a string.' unless settings[:pw].is_a?(String)
|
77
|
-
File.file?(settings[:file]) ? settings[:file] = File.read(settings[:file]) : (raise 'Input file is not an existing file.')
|
78
76
|
end
|
79
77
|
end
|
@@ -4,8 +4,14 @@ require_relative '../../lib/rapid-vaults/decrypt'
|
|
4
4
|
|
5
5
|
describe Decrypt do
|
6
6
|
context '.openssl' do
|
7
|
+
require 'openssl'
|
8
|
+
require 'securerandom'
|
9
|
+
cipher = OpenSSL::Cipher.new('aes-256-gcm').encrypt
|
10
|
+
key = cipher.random_key
|
11
|
+
nonce = cipher.random_iv
|
12
|
+
|
7
13
|
before(:all) do
|
8
|
-
Encrypt.openssl(ui: :cli, file: "foo: bar\n", key:
|
14
|
+
Encrypt.openssl(ui: :cli, file: "foo: bar\n", key: key, nonce: nonce)
|
9
15
|
end
|
10
16
|
|
11
17
|
after(:all) do
|
@@ -13,22 +19,31 @@ describe Decrypt do
|
|
13
19
|
end
|
14
20
|
|
15
21
|
it 'outputs a decrypted file with the key, nonce, and tag from the cli' do
|
16
|
-
Decrypt.openssl(ui: :cli, file: File.read('encrypted.txt'), key:
|
22
|
+
Decrypt.openssl(ui: :cli, file: File.read('encrypted.txt'), key: key, nonce: nonce, tag: File.read('tag.txt'))
|
17
23
|
expect(File.file?('decrypted.txt')).to be true
|
18
24
|
expect(File.read('decrypted.txt')).to eq("foo: bar\n")
|
19
25
|
end
|
20
26
|
it 'outputs decrypted content with the key, nonce, and tag from the api' do
|
21
|
-
decrypt = Decrypt.openssl(ui: :api, file: File.read('encrypted.txt'), key:
|
27
|
+
decrypt = Decrypt.openssl(ui: :api, file: File.read('encrypted.txt'), key: key, nonce: nonce, tag: File.read('tag.txt'))
|
22
28
|
expect(decrypt).to be_a(String)
|
23
29
|
expect(decrypt).to eq("foo: bar\n")
|
24
30
|
end
|
25
31
|
it 'raises an error for an invalid tag size' do
|
26
|
-
expect { Decrypt.openssl(file: File.read('encrypted.txt'), key:
|
32
|
+
expect { Decrypt.openssl(file: File.read('encrypted.txt'), key: key, nonce: nonce, tag: SecureRandom.random_bytes(24).strip) }.to raise_error('Tag is not 16 bytes.')
|
33
|
+
end
|
34
|
+
it 'raises an error for an invalid key size' do
|
35
|
+
expect { Decrypt.openssl(key: SecureRandom.random_bytes(64).strip) }.to raise_error('The key is not a valid 32 byte key.')
|
36
|
+
end
|
37
|
+
it 'raises an error for an invalid nonce size' do
|
38
|
+
expect { Decrypt.openssl(key: key, nonce: SecureRandom.random_bytes(24).strip) }.to raise_error('The nonce is not a valid 12 byte nonce.')
|
39
|
+
end
|
40
|
+
it 'raises an error for corrupted encrypted file content' do
|
41
|
+
expect { Decrypt.openssl(file: SecureRandom.random_bytes(16).strip, key: key, nonce: nonce) }.to raise_error('The encrypted data is not a valid multiple of 9 bytes.')
|
27
42
|
end
|
28
43
|
end
|
29
44
|
|
30
45
|
# travis ci cannot support non-interactive gpg encryption
|
31
|
-
unless
|
46
|
+
unless ENV['TRAVIS'] == 'true'
|
32
47
|
context '.gpgme' do
|
33
48
|
before(:all) do
|
34
49
|
Encrypt.gpgme(ui: :cli, file: "foo: bar\n", key: '', pw: 'foo')
|
@@ -3,31 +3,43 @@ require_relative '../../lib/rapid-vaults/encrypt'
|
|
3
3
|
|
4
4
|
describe Encrypt do
|
5
5
|
context '.openssl' do
|
6
|
+
require 'openssl'
|
7
|
+
require 'securerandom'
|
8
|
+
cipher = OpenSSL::Cipher.new('aes-256-gcm').encrypt
|
9
|
+
key = cipher.random_key
|
10
|
+
nonce = cipher.random_iv
|
11
|
+
|
6
12
|
after(:all) do
|
7
13
|
%w[tag.txt encrypted.txt].each { |file| File.delete(file) }
|
8
14
|
end
|
9
15
|
|
10
16
|
it 'outputs an encrypted file with the key and nonce from the cli' do
|
11
|
-
Encrypt.openssl(ui: :cli, file: "foo: bar\n", key:
|
17
|
+
Encrypt.openssl(ui: :cli, file: "foo: bar\n", key: key, nonce: nonce)
|
12
18
|
expect(File.file?('tag.txt')).to be true
|
13
19
|
expect(File.file?('encrypted.txt')).to be true
|
14
20
|
end
|
15
21
|
it 'outputs an encrypted file with the key, nonce, and password from the cli' do
|
16
|
-
Encrypt.openssl(ui: :cli, file: "foo: bar\n", key:
|
22
|
+
Encrypt.openssl(ui: :cli, file: "foo: bar\n", key: key, nonce: nonce, pw: 'password')
|
17
23
|
expect(File.file?('tag.txt')).to be true
|
18
24
|
expect(File.file?('encrypted.txt')).to be true
|
19
25
|
end
|
20
26
|
it 'outputs an array of encrypted content and tag with the key and nonce from the api' do
|
21
|
-
encrypt = Encrypt.openssl(ui: :api, file: "foo: bar\n", key:
|
27
|
+
encrypt = Encrypt.openssl(ui: :api, file: "foo: bar\n", key: key, nonce: nonce)
|
22
28
|
expect(encrypt).to be_a(Array)
|
23
29
|
expect(encrypt[0]).to be_a(String)
|
24
30
|
expect(encrypt[1]).to be_a(String)
|
25
31
|
expect(encrypt.length).to eq(2)
|
26
32
|
end
|
33
|
+
it 'raises an error for an invalid key size' do
|
34
|
+
expect { Encrypt.openssl(key: SecureRandom.random_bytes(64).strip) }.to raise_error('The key is not a valid 32 byte key.')
|
35
|
+
end
|
36
|
+
it 'raises an error for an invalid nonce size' do
|
37
|
+
expect { Encrypt.openssl(key: key, nonce: SecureRandom.random_bytes(24).strip) }.to raise_error('The nonce is not a valid 12 byte nonce.')
|
38
|
+
end
|
27
39
|
end
|
28
40
|
|
29
41
|
# travis ci cannot support non-interactive gpg encryption
|
30
|
-
unless
|
42
|
+
unless ENV['TRAVIS'] == 'true'
|
31
43
|
context '.gpgme' do
|
32
44
|
it 'outputs an encrypted file with the key from the cli' do
|
33
45
|
Encrypt.gpgme(ui: :cli, file: "foo: bar\n", key: '', pw: 'foo')
|
@@ -28,7 +28,7 @@ describe Generate do
|
|
28
28
|
expect { Generate.gpgme(gpgparams: File.read("#{fixtures_dir}/gpgparams.txt")) }.to raise_error('Environment variable "GNUPGHOME" was not set.')
|
29
29
|
end
|
30
30
|
# travis ci cannot support non-interactive gpg
|
31
|
-
unless
|
31
|
+
unless ENV['TRAVIS'] == 'true'
|
32
32
|
it 'generates the key files' do
|
33
33
|
require 'fileutils'
|
34
34
|
|
@@ -0,0 +1,42 @@
|
|
1
|
+
require_relative '../../lib/rapid-vaults/grpc'
|
2
|
+
|
3
|
+
# TODO: use RapidVaults::GRPC.server instead?
|
4
|
+
stub = Rapidvaults::RapidVaults::Stub.new('localhost:0.0.0.0:8080', :this_channel_is_insecure)
|
5
|
+
|
6
|
+
# need to create class with encode member method to pass in as dummy
|
7
|
+
# ssl generate
|
8
|
+
# outputs = stub.ssl_generate('string')
|
9
|
+
=begin
|
10
|
+
puts outputs.key
|
11
|
+
puts outputs.nonce
|
12
|
+
|
13
|
+
# gpg generate
|
14
|
+
stub.gpg_generate
|
15
|
+
|
16
|
+
# ssl encrypt
|
17
|
+
# TODO: unencrypted should be an object
|
18
|
+
unencrypted.text = ''
|
19
|
+
unencrypted.key = ''
|
20
|
+
unencrypted.nonce = ''
|
21
|
+
outputs = stub.ssl_encrypt(unencrypted)
|
22
|
+
puts outputs.text
|
23
|
+
puts outputs.tag
|
24
|
+
|
25
|
+
# gpg encrypt
|
26
|
+
unencrypted.text = ''
|
27
|
+
unencrypted.password = ''
|
28
|
+
puts stub.gpg_encrypt(unencrypted).text
|
29
|
+
|
30
|
+
# ssl decrypt
|
31
|
+
# TODO: undecrypted should be an object
|
32
|
+
undecrypted.text = ''
|
33
|
+
undecrypted.key = ''
|
34
|
+
undecrypted.nonce = ''
|
35
|
+
undecrypted.tag = ''
|
36
|
+
puts stub.ssl_decrypt(undecrypted).text
|
37
|
+
|
38
|
+
# gpg decrypt
|
39
|
+
undecrypted.text = ''
|
40
|
+
undecrypted.password = ''
|
41
|
+
puts stub.gpg_decrypt(undecrypted).text
|
42
|
+
=end
|
@@ -1,11 +1,17 @@
|
|
1
1
|
require_relative 'spec_helper'
|
2
|
-
require_relative '../lib/
|
2
|
+
require_relative '../lib/rapid_vaults'
|
3
3
|
|
4
4
|
describe RapidVaults do
|
5
5
|
context '.process' do
|
6
6
|
it 'raises an error for a non-string password with openssl' do
|
7
7
|
expect { RapidVaults.process(action: :encrypt, file: 'a', key: 'b', nonce: 'c', pw: 1) }.to raise_error('Password must be a string.')
|
8
8
|
end
|
9
|
+
it 'raises an error for a non-string password with gpgme' do
|
10
|
+
expect { RapidVaults.process(action: :encrypt, file: 'a', key: 'b', nonce: 'c', pw: 1) }.to raise_error('Password must be a string.')
|
11
|
+
end
|
12
|
+
it 'raises an error for a missing argument to generate with gpgme' do
|
13
|
+
expect { RapidVaults.process(algorithm: :gpgme, action: :generate) }.to raise_error('GPG params file argument required for generation.')
|
14
|
+
end
|
9
15
|
it 'raises an error for a missing argument to encrypt with openssl' do
|
10
16
|
expect { RapidVaults.process(action: :encrypt, file: 'a', key: 'b') }.to raise_error('File, key, and nonce arguments are required for encryption.')
|
11
17
|
end
|
@@ -21,18 +27,18 @@ describe RapidVaults do
|
|
21
27
|
it 'raises an error for a missing action with gpgme' do
|
22
28
|
expect { RapidVaults.process(algorithm: :gpgme, file: 'a', key: 'b') }.to raise_error('Action must be one of generate, encrypt, or decrypt.')
|
23
29
|
end
|
24
|
-
it 'raises an error for a
|
25
|
-
expect { RapidVaults.process(
|
30
|
+
it 'raises an error for a nonexistent input file with openssl' do
|
31
|
+
expect { RapidVaults.process(action: :encrypt, file: 'a', key: 'b', nonce: 'c', tag: 'd') }.to raise_error('Input file \'a\' for argument \'file\' is not an existing readable file.')
|
26
32
|
end
|
27
|
-
it 'raises an error for a nonexistent input file' do
|
28
|
-
expect { RapidVaults.process(
|
33
|
+
it 'raises an error for a nonexistent input file with gpgme' do
|
34
|
+
expect { RapidVaults.process(algorithm: :gpgme, action: :encrypt, file: 'a', pw: 'password') }.to raise_error('Input file \'a\' for argument \'file\' is not an existing readable file.')
|
29
35
|
end
|
30
36
|
it 'reads in all input files correctly for openssl encryption' do
|
31
|
-
dummy = fixtures_dir
|
37
|
+
dummy = "#{fixtures_dir}file.yaml"
|
32
38
|
expect { RapidVaults.process(action: :encrypt, file: dummy, key: dummy, nonce: dummy, pw: 'password') }.not_to raise_exception
|
33
39
|
end
|
34
40
|
it 'reads in all input files correctly for gpgme decryption' do
|
35
|
-
dummy = fixtures_dir
|
41
|
+
dummy = "#{fixtures_dir}file.yaml"
|
36
42
|
expect { RapidVaults.process(algorithm: :gpgme, action: :decrypt, file: dummy, pw: 'password') }.not_to raise_exception
|
37
43
|
end
|
38
44
|
end
|
data/spec/spec_helper.rb
CHANGED
data/spec/system/system_spec.rb
CHANGED
@@ -7,13 +7,13 @@ describe RapidVaults do
|
|
7
7
|
require 'fileutils'
|
8
8
|
|
9
9
|
%w[key.txt nonce.txt tag.txt encrypted.txt decrypted.txt chef.rb puppet_gpg_decrypt.rb puppet_gpg_encrypt.rb puppet_ssl_decrypt.rb puppet_ssl_encrypt.rb].each { |file| File.delete(file) }
|
10
|
-
unless
|
11
|
-
%w[random_seed pubring.kbx trustdb.gpg pubring.kbx~
|
10
|
+
unless ENV['TRAVIS'] == 'true' || ENV['CIRCLECI'] == 'true' || ENV['GITHUB_ACTIONS'] == 'true'
|
11
|
+
%w[random_seed pubring.kbx trustdb.gpg pubring.kbx~].each { |file| File.delete(file) }
|
12
12
|
%w[openpgp-revocs.d private-keys-v1.d].each { |dir| FileUtils.rm_r(dir) }
|
13
13
|
end
|
14
14
|
end
|
15
15
|
|
16
|
-
context 'executed as a system from the CLI with settings and a file to be processed' do
|
16
|
+
context 'executed with openssl algorithm as a system from the CLI with settings and a file to be processed' do
|
17
17
|
it 'generates key and nonce, encrypts a file, and then decrypts a file in order' do
|
18
18
|
# generate and utilize files inside suitable directory
|
19
19
|
Dir.chdir(fixtures_dir)
|
@@ -35,7 +35,7 @@ describe RapidVaults do
|
|
35
35
|
end
|
36
36
|
end
|
37
37
|
|
38
|
-
context 'executed as a system from the API with settings and a file to be processed' do
|
38
|
+
context 'executed with openssl algorithm as a system from the API with settings and a file to be processed' do
|
39
39
|
it 'generates key and nonce, encrypts a file, and then decrypts a file in order' do
|
40
40
|
# generate and utilize files inside suitable directory
|
41
41
|
Dir.chdir(fixtures_dir)
|
@@ -59,9 +59,9 @@ describe RapidVaults do
|
|
59
59
|
end
|
60
60
|
end
|
61
61
|
|
62
|
-
#
|
63
|
-
unless
|
64
|
-
context 'executed wtih gpg as a system from the CLI with settings and a file to be processed' do
|
62
|
+
# all three ci cannot support end-to-end gpg generate/encrypt/decrypt
|
63
|
+
unless ENV['TRAVIS'] == 'true' || ENV['CIRCLECI'] == 'true' || ENV['GITHUB_ACTIONS'] == 'true'
|
64
|
+
context 'executed wtih gpg algorithm as a system from the CLI with settings and a file to be processed' do
|
65
65
|
it 'encrypts a file and then decrypts a file in order' do
|
66
66
|
ENV['GNUPGHOME'] = fixtures_dir
|
67
67
|
|
@@ -86,7 +86,7 @@ describe RapidVaults do
|
|
86
86
|
end
|
87
87
|
end
|
88
88
|
|
89
|
-
context 'executed with gpg as a system from the API with settings and a file to be processed' do
|
89
|
+
context 'executed with gpg algorithm as a system from the API with settings and a file to be processed' do
|
90
90
|
it 'encrypts a file and then decrypts a file in order' do
|
91
91
|
ENV['GNUPGHOME'] = fixtures_dir
|
92
92
|
|
@@ -94,7 +94,7 @@ describe RapidVaults do
|
|
94
94
|
Dir.chdir(fixtures_dir)
|
95
95
|
|
96
96
|
# generate keys
|
97
|
-
RapidVaults::API.main(action: :generate, algorithm: :gpgme, gpgparams: File.read('gpgparams.txt')
|
97
|
+
RapidVaults::API.main(action: :generate, algorithm: :gpgme, gpgparams: File.read('gpgparams.txt'))
|
98
98
|
%w[trustdb.gpg pubring.kbx pubring.kbx~].each { |file| expect(File.file?("#{fixtures_dir}/#{file}")).to be true }
|
99
99
|
%w[openpgp-revocs.d private-keys-v1.d].each { |dir| expect(File.directory?("#{fixtures_dir}/#{dir}")).to be true }
|
100
100
|
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: rapid-vaults
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 1.
|
4
|
+
version: 1.2.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Matt Schuchard
|
8
|
-
autorequire:
|
8
|
+
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date:
|
11
|
+
date: 2022-08-05 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: gpgme
|
@@ -25,45 +25,61 @@ dependencies:
|
|
25
25
|
- !ruby/object:Gem::Version
|
26
26
|
version: '2.0'
|
27
27
|
- !ruby/object:Gem::Dependency
|
28
|
-
name:
|
28
|
+
name: grpc
|
29
29
|
requirement: !ruby/object:Gem::Requirement
|
30
30
|
requirements:
|
31
|
-
- - "
|
31
|
+
- - "~>"
|
32
32
|
- !ruby/object:Gem::Version
|
33
|
-
version: '
|
34
|
-
|
33
|
+
version: '1.0'
|
34
|
+
type: :development
|
35
|
+
prerelease: false
|
36
|
+
version_requirements: !ruby/object:Gem::Requirement
|
37
|
+
requirements:
|
38
|
+
- - "~>"
|
35
39
|
- !ruby/object:Gem::Version
|
36
|
-
version: '
|
40
|
+
version: '1.0'
|
41
|
+
- !ruby/object:Gem::Dependency
|
42
|
+
name: grpc-tools
|
43
|
+
requirement: !ruby/object:Gem::Requirement
|
44
|
+
requirements:
|
45
|
+
- - "~>"
|
46
|
+
- !ruby/object:Gem::Version
|
47
|
+
version: '1.0'
|
37
48
|
type: :development
|
38
49
|
prerelease: false
|
39
50
|
version_requirements: !ruby/object:Gem::Requirement
|
40
51
|
requirements:
|
41
|
-
- - "
|
52
|
+
- - "~>"
|
42
53
|
- !ruby/object:Gem::Version
|
43
|
-
version: '
|
44
|
-
|
54
|
+
version: '1.0'
|
55
|
+
- !ruby/object:Gem::Dependency
|
56
|
+
name: rake
|
57
|
+
requirement: !ruby/object:Gem::Requirement
|
58
|
+
requirements:
|
59
|
+
- - "~>"
|
45
60
|
- !ruby/object:Gem::Version
|
46
|
-
version: '
|
61
|
+
version: '12.0'
|
62
|
+
type: :development
|
63
|
+
prerelease: false
|
64
|
+
version_requirements: !ruby/object:Gem::Requirement
|
65
|
+
requirements:
|
66
|
+
- - "~>"
|
67
|
+
- !ruby/object:Gem::Version
|
68
|
+
version: '12.0'
|
47
69
|
- !ruby/object:Gem::Dependency
|
48
70
|
name: reek
|
49
71
|
requirement: !ruby/object:Gem::Requirement
|
50
72
|
requirements:
|
51
|
-
- - "
|
52
|
-
- !ruby/object:Gem::Version
|
53
|
-
version: '4.0'
|
54
|
-
- - "<"
|
73
|
+
- - "~>"
|
55
74
|
- !ruby/object:Gem::Version
|
56
|
-
version: '6'
|
75
|
+
version: '6.0'
|
57
76
|
type: :development
|
58
77
|
prerelease: false
|
59
78
|
version_requirements: !ruby/object:Gem::Requirement
|
60
79
|
requirements:
|
61
|
-
- - "
|
62
|
-
- !ruby/object:Gem::Version
|
63
|
-
version: '4.0'
|
64
|
-
- - "<"
|
80
|
+
- - "~>"
|
65
81
|
- !ruby/object:Gem::Version
|
66
|
-
version: '6'
|
82
|
+
version: '6.0'
|
67
83
|
- !ruby/object:Gem::Dependency
|
68
84
|
name: rspec
|
69
85
|
requirement: !ruby/object:Gem::Requirement
|
@@ -80,21 +96,41 @@ dependencies:
|
|
80
96
|
version: '3.0'
|
81
97
|
- !ruby/object:Gem::Dependency
|
82
98
|
name: rubocop
|
99
|
+
requirement: !ruby/object:Gem::Requirement
|
100
|
+
requirements:
|
101
|
+
- - ">="
|
102
|
+
- !ruby/object:Gem::Version
|
103
|
+
version: '0.58'
|
104
|
+
- - "<"
|
105
|
+
- !ruby/object:Gem::Version
|
106
|
+
version: '2'
|
107
|
+
type: :development
|
108
|
+
prerelease: false
|
109
|
+
version_requirements: !ruby/object:Gem::Requirement
|
110
|
+
requirements:
|
111
|
+
- - ">="
|
112
|
+
- !ruby/object:Gem::Version
|
113
|
+
version: '0.58'
|
114
|
+
- - "<"
|
115
|
+
- !ruby/object:Gem::Version
|
116
|
+
version: '2'
|
117
|
+
- !ruby/object:Gem::Dependency
|
118
|
+
name: rubocop-performance
|
83
119
|
requirement: !ruby/object:Gem::Requirement
|
84
120
|
requirements:
|
85
121
|
- - "~>"
|
86
122
|
- !ruby/object:Gem::Version
|
87
|
-
version: '0
|
123
|
+
version: '1.0'
|
88
124
|
type: :development
|
89
125
|
prerelease: false
|
90
126
|
version_requirements: !ruby/object:Gem::Requirement
|
91
127
|
requirements:
|
92
128
|
- - "~>"
|
93
129
|
- !ruby/object:Gem::Version
|
94
|
-
version: '0
|
130
|
+
version: '1.0'
|
95
131
|
description: Ad-hoc encrypt and decrypt data behind multiple layers of protection
|
96
132
|
via OpenSSL or GPG.
|
97
|
-
email:
|
133
|
+
email:
|
98
134
|
executables:
|
99
135
|
- rapid-vaults
|
100
136
|
extensions: []
|
@@ -102,7 +138,6 @@ extra_rdoc_files: []
|
|
102
138
|
files:
|
103
139
|
- README.md
|
104
140
|
- bin/rapid-vaults
|
105
|
-
- lib/rapid-vaults.rb
|
106
141
|
- lib/rapid-vaults/api.rb
|
107
142
|
- lib/rapid-vaults/binding.rb
|
108
143
|
- lib/rapid-vaults/bindings/chef.rb
|
@@ -114,6 +149,8 @@ files:
|
|
114
149
|
- lib/rapid-vaults/decrypt.rb
|
115
150
|
- lib/rapid-vaults/encrypt.rb
|
116
151
|
- lib/rapid-vaults/generate.rb
|
152
|
+
- lib/rapid-vaults/grpc.rb
|
153
|
+
- lib/rapid_vaults.rb
|
117
154
|
- spec/fixtures/file.yaml
|
118
155
|
- spec/fixtures/gpgparams.txt
|
119
156
|
- spec/rapid-vaults/api_spec.rb
|
@@ -122,14 +159,15 @@ files:
|
|
122
159
|
- spec/rapid-vaults/decrypt_spec.rb
|
123
160
|
- spec/rapid-vaults/encrypt_spec.rb
|
124
161
|
- spec/rapid-vaults/generate_spec.rb
|
125
|
-
- spec/rapid-
|
162
|
+
- spec/rapid-vaults/grpc_spec.rb
|
163
|
+
- spec/rapid_vaults_spec.rb
|
126
164
|
- spec/spec_helper.rb
|
127
165
|
- spec/system/system_spec.rb
|
128
166
|
homepage: https://www.github.com/mschuchard/rapid-vaults
|
129
167
|
licenses:
|
130
168
|
- MIT
|
131
169
|
metadata: {}
|
132
|
-
post_install_message:
|
170
|
+
post_install_message:
|
133
171
|
rdoc_options: []
|
134
172
|
require_paths:
|
135
173
|
- lib
|
@@ -137,16 +175,15 @@ required_ruby_version: !ruby/object:Gem::Requirement
|
|
137
175
|
requirements:
|
138
176
|
- - ">="
|
139
177
|
- !ruby/object:Gem::Version
|
140
|
-
version: 2.
|
178
|
+
version: 2.5.0
|
141
179
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
142
180
|
requirements:
|
143
181
|
- - ">="
|
144
182
|
- !ruby/object:Gem::Version
|
145
183
|
version: '0'
|
146
184
|
requirements: []
|
147
|
-
|
148
|
-
|
149
|
-
signing_key:
|
185
|
+
rubygems_version: 3.3.5
|
186
|
+
signing_key:
|
150
187
|
specification_version: 4
|
151
188
|
summary: Ad-hoc encrypt and decrypt data.
|
152
189
|
test_files:
|
@@ -158,6 +195,7 @@ test_files:
|
|
158
195
|
- spec/rapid-vaults/decrypt_spec.rb
|
159
196
|
- spec/rapid-vaults/encrypt_spec.rb
|
160
197
|
- spec/rapid-vaults/generate_spec.rb
|
161
|
-
- spec/rapid-
|
198
|
+
- spec/rapid-vaults/grpc_spec.rb
|
199
|
+
- spec/rapid_vaults_spec.rb
|
162
200
|
- spec/spec_helper.rb
|
163
201
|
- spec/system/system_spec.rb
|