hiera-eyaml-twofac 0.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA1:
3
+ metadata.gz: 4c443add06611322dd097c1f443c49151fed7446
4
+ data.tar.gz: cb0d1664ec347550d5cdace5f8eeb82226ddf7b9
5
+ SHA512:
6
+ metadata.gz: 0e53ea4fb8afd71e61a3c8483ecac4a2daeeaf13de7672777dba2c13d5dfe3a7140e42c38e60c282459549bc8e64f94c3c35189abbf77aa99a0f50cb80c20e46
7
+ data.tar.gz: 0f07b294518b9ff8a506d69ee09951aec54e7bec6ac1a834682884562628e9906e20ca7a66771c51b34eea78cdf10895a7cf8921d42e895fc0dfe677f14e6050
data/.gitignore ADDED
@@ -0,0 +1 @@
1
+ .ruby-version
data/Gemfile ADDED
@@ -0,0 +1,10 @@
1
+ source 'https://rubygems.org/'
2
+
3
+ gem "openssl"
4
+ gem "digest"
5
+ gem "highline"
6
+
7
+ group :development do
8
+ gem "aruba"
9
+ end
10
+
data/Gemfile.lock ADDED
@@ -0,0 +1,36 @@
1
+ GEM
2
+ remote: https://rubygems.org/
3
+ specs:
4
+ aruba (0.5.3)
5
+ childprocess (>= 0.3.6)
6
+ cucumber (>= 1.1.1)
7
+ rspec-expectations (>= 2.7.0)
8
+ builder (3.2.2)
9
+ childprocess (0.3.9)
10
+ ffi (~> 1.0, >= 1.0.11)
11
+ cucumber (1.3.10)
12
+ builder (>= 2.1.2)
13
+ diff-lcs (>= 1.1.3)
14
+ gherkin (~> 2.12)
15
+ multi_json (>= 1.7.5, < 2.0)
16
+ multi_test (>= 0.0.2)
17
+ diff-lcs (1.2.5)
18
+ digest (0.0.1)
19
+ ffi (1.9.3)
20
+ gherkin (2.12.2)
21
+ multi_json (~> 1.3)
22
+ highline (1.6.21)
23
+ multi_json (1.8.2)
24
+ multi_test (0.0.2)
25
+ openssl (1.0.0.beta)
26
+ rspec-expectations (2.14.4)
27
+ diff-lcs (>= 1.1.3, < 2.0)
28
+
29
+ PLATFORMS
30
+ ruby
31
+
32
+ DEPENDENCIES
33
+ aruba
34
+ digest
35
+ highline
36
+ openssl
data/LICENSE.txt ADDED
@@ -0,0 +1,22 @@
1
+
2
+ The MIT License (MIT)
3
+
4
+ Copyright (c) 2013 GTMTech Ltd
5
+
6
+ Permission is hereby granted, free of charge, to any person obtaining a copy of
7
+ this software and associated documentation files (the "Software"), to deal in
8
+ the Software without restriction, including without limitation the rights to
9
+ use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
10
+ the Software, and to permit persons to whom the Software is furnished to do so,
11
+ subject to the following conditions:
12
+
13
+ The above copyright notice and this permission notice shall be included in all
14
+ copies or substantial portions of the Software.
15
+
16
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
18
+ FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
19
+ COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
20
+ IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
21
+ CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
22
+
data/README.md ADDED
@@ -0,0 +1,43 @@
1
+ hiera-eyaml-twofac
2
+ ==================
3
+
4
+ This is a plugin encryptor for the hiera-eyaml project (hosted https://github.com/TomPoulton/hiera-eyaml/).
5
+
6
+ It encrypts using the pkcs7 encryption type (much like the existing encryptor) - however it also requires an interactive password to be supplied at runtime. This makes it fairly useless in puppet scenarios, however eyaml as a tool is useful in other scenarios.
7
+
8
+ Usage:
9
+
10
+ ```
11
+ $ gem install hiera-eyaml-twofac
12
+ ```
13
+
14
+ Then see hiera-eyaml documentation for how to use the eyaml tool to encrypt using the 'TWOFAC' encryption_type.
15
+
16
+ Authors
17
+ =======
18
+
19
+ - [Geoff Meakin](http://github.com/gtmtechltd)
20
+
21
+ License
22
+ =======
23
+
24
+ The MIT License (MIT)
25
+
26
+ Copyright (c) 2013 GTMTech Ltd
27
+
28
+ Permission is hereby granted, free of charge, to any person obtaining a copy of
29
+ this software and associated documentation files (the "Software"), to deal in
30
+ the Software without restriction, including without limitation the rights to
31
+ use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
32
+ the Software, and to permit persons to whom the Software is furnished to do so,
33
+ subject to the following conditions:
34
+
35
+ The above copyright notice and this permission notice shall be included in all
36
+ copies or substantial portions of the Software.
37
+
38
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
39
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
40
+ FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
41
+ COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
42
+ IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
43
+ CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
data/Rakefile ADDED
@@ -0,0 +1 @@
1
+ require "bundler/gem_tasks"
@@ -0,0 +1,19 @@
1
+ # -*- encoding: utf-8 -*-
2
+ lib = File.expand_path('../lib', __FILE__)
3
+ $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
4
+ require 'hiera/backend/eyaml/encryptors/twofac'
5
+
6
+ Gem::Specification.new do |gem|
7
+ gem.name = "hiera-eyaml-twofac"
8
+ gem.version = Hiera::Backend::Eyaml::Encryptors::Twofac::VERSION
9
+ gem.description = "PKCS7 + AES256 2-factor encryptor for use with hiera-eyaml"
10
+ gem.summary = "Encryption plugin for hiera-eyaml backend for Hiera"
11
+ gem.author = "Geoff Meakin"
12
+ gem.license = "MIT"
13
+
14
+ gem.homepage = "http://github.com/gtmtechltd/hiera-eyaml-twofac"
15
+ gem.files = `git ls-files`.split($/)
16
+ gem.executables = gem.files.grep(%r{^bin/}).map{ |f| File.basename(f) }
17
+ gem.test_files = gem.files.grep(%r{^(test|spec|features)/})
18
+ gem.require_paths = ["lib"]
19
+ end
@@ -0,0 +1,180 @@
1
+ require 'base64'
2
+ require 'openssl'
3
+ require 'digest'
4
+ require 'hiera/backend/eyaml/encryptor'
5
+ require 'hiera/backend/eyaml/utils'
6
+ require 'hiera/backend/eyaml/options'
7
+ require 'hiera/backend/eyaml/encryptors/twofac_utils/password'
8
+
9
+ class Hiera
10
+ module Backend
11
+ module Eyaml
12
+ module Encryptors
13
+
14
+ class Twofac < Encryptor
15
+
16
+ VERSION = "0.1"
17
+
18
+ self.tag = "TWOFAC"
19
+ self.options = {
20
+ :twofac_private_key => { :desc => "Path to twofac private key",
21
+ :type => :string,
22
+ :default => "./keys/private_key.twofac.txt" },
23
+ :twofac_public_key => { :desc => "Path to twofac public key",
24
+ :type => :string,
25
+ :default => "./keys/public_key.twofac.pem" },
26
+ :twofac_subject => { :desc => "Subject to use for twofac certificate when creating keys",
27
+ :type => :string,
28
+ :default => "/" },
29
+ }
30
+
31
+ @@vector = "5geLmxqskV0Ruf1ZeRAwvw=="
32
+
33
+ def self.encrypt plaintext
34
+
35
+ password = Hiera::Backend::Eyaml::Encryptors::TwofacUtils::Password.obtain
36
+
37
+ #TODO: delegate this to original pkcs7 plugin
38
+ public_key = self.option :twofac_public_key
39
+ raise StandardError, "twofac_public_key is not defined" unless public_key
40
+
41
+ public_key_pem = File.read public_key
42
+ public_key_x509 = OpenSSL::X509::Certificate.new( public_key_pem )
43
+
44
+ cipher = OpenSSL::Cipher::AES.new(256, :CBC)
45
+ OpenSSL::PKCS7::encrypt([public_key_x509], plaintext, cipher, OpenSSL::PKCS7::BINARY).to_der
46
+
47
+ end
48
+
49
+ def self.decrypt ciphertext
50
+
51
+ password = Hiera::Backend::Eyaml::Encryptors::TwofacUtils::Password.obtain
52
+
53
+ #TODO: delegate this to original pkcs7 plugin
54
+ public_key = self.option :twofac_public_key
55
+ private_key = self.option :twofac_private_key
56
+ raise StandardError, "twofac_public_key is not defined" unless public_key
57
+ raise StandardError, "twofac_private_key is not defined" unless private_key
58
+
59
+ begin
60
+ private_key_input = File.read private_key
61
+ rescue
62
+ raise StandardError, "Unable to read contents of keyfile #{private_key}. Check permissions"
63
+ end
64
+
65
+ unless private_key_input.include? "-----BEGIN TWOFAC KEY-----" and private_key_input.include? "-----END TWOFAC KEY-----"
66
+ raise StandardError, "Keyfile #{private_key} is not a TWOFAC key file"
67
+ end
68
+
69
+ begin
70
+ private_key_base64 = private_key_input.split('-----BEGIN TWOFAC KEY-----')[1].split('-----END TWOFAC KEY-----')[0]
71
+ private_key_aes = Base64.decode64(private_key_base64)
72
+ private_key_pem = aes_decrypt( password, private_key_aes)
73
+ private_key_rsa = OpenSSL::PKey::RSA.new( private_key_pem )
74
+ rescue
75
+ password = ""
76
+ private_key_base64 = ""
77
+ private_key_aes = ""
78
+ private_key_pem = ""
79
+ private_key_rsa = ""
80
+ raise StandardError, "Unable to decrypt keyfile #{private_key} with password"
81
+ end
82
+
83
+ public_key_pem = File.read public_key
84
+ public_key_x509 = OpenSSL::X509::Certificate.new( public_key_pem )
85
+
86
+ begin
87
+ pkcs7 = OpenSSL::PKCS7.new( ciphertext )
88
+ pkcs7.decrypt(private_key_rsa, public_key_x509)
89
+ rescue
90
+ raise StandardError, "Unable to decipher using supplied key"
91
+ end
92
+
93
+ end
94
+
95
+ def self.create_keys
96
+
97
+ password = Hiera::Backend::Eyaml::Encryptors::TwofacUtils::Password.obtain
98
+
99
+ #TODO: delegate this to original pkcs7 plugin
100
+
101
+ # Try to do equivalent of:
102
+ # openssl req -x509 -nodes -days 100000 -newkey rsa:2048 -keyout privatekey.pem -out publickey.pem -subj '/'
103
+
104
+ public_key = self.option :twofac_public_key
105
+ private_key = self.option :twofac_private_key
106
+ subject = self.option :twofac_subject
107
+
108
+ key = OpenSSL::PKey::RSA.new(2048)
109
+ Utils.ensure_key_dir_exists private_key
110
+ pem_data = key.to_pem
111
+ aes_data = aes_encrypt( password, pem_data )
112
+ base64_data = Base64.encode64(aes_data).strip
113
+ output_data = ["-----BEGIN TWOFAC KEY-----", base64_data, "-----END TWOFAC KEY-----"].join("\n")
114
+
115
+ Utils.write_important_file :filename => private_key, :content => output_data, :mode => 0600
116
+
117
+ password = ""
118
+ pem_data = ""
119
+ aes_data = ""
120
+ base64_data = ""
121
+
122
+ cert = OpenSSL::X509::Certificate.new()
123
+ cert.subject = OpenSSL::X509::Name.parse(subject)
124
+ cert.serial = 1
125
+ cert.version = 2
126
+ cert.not_before = Time.now
127
+ cert.not_after = if 1.size == 8 # 64bit
128
+ Time.now + 50 * 365 * 24 * 60 * 60
129
+ else # 32bit
130
+ Time.at(0x7fffffff)
131
+ end
132
+ cert.public_key = key.public_key
133
+
134
+ ef = OpenSSL::X509::ExtensionFactory.new
135
+ ef.subject_certificate = cert
136
+ ef.issuer_certificate = cert
137
+ cert.extensions = [
138
+ ef.create_extension("basicConstraints","CA:TRUE", true),
139
+ ef.create_extension("subjectKeyIdentifier", "hash"),
140
+ ]
141
+ cert.add_extension ef.create_extension("authorityKeyIdentifier",
142
+ "keyid:always,issuer:always")
143
+
144
+ cert.sign key, OpenSSL::Digest::SHA1.new
145
+
146
+ Utils.ensure_key_dir_exists public_key
147
+ Utils.write_important_file :filename => public_key, :content => cert.to_pem
148
+ puts "Keys created OK"
149
+ end
150
+
151
+ def self.aes_decrypt(password, data)
152
+ key = Digest::SHA256.digest password
153
+ iv = Digest::MD5.digest @@vector
154
+ aes = OpenSSL::Cipher.new('AES-256-CBC')
155
+ aes.decrypt
156
+ aes.key = key
157
+ aes.iv = iv
158
+ aes.update(data) + aes.final
159
+ end
160
+
161
+ def self.aes_encrypt(password, data)
162
+ key = Digest::SHA256.digest password
163
+ iv = Digest::MD5.digest @@vector
164
+ aes = OpenSSL::Cipher.new('AES-256-CBC')
165
+ aes.encrypt
166
+ aes.key = key
167
+ aes.iv = iv
168
+ aes.update(data) + aes.final
169
+ end
170
+
171
+ end
172
+
173
+ end
174
+
175
+ end
176
+
177
+ end
178
+
179
+ end
180
+
@@ -0,0 +1,3 @@
1
+ require 'hiera/backend/eyaml/encryptors/twofac'
2
+
3
+ Hiera::Backend::Eyaml::Encryptors::Twofac.register
@@ -0,0 +1,27 @@
1
+ require 'highline/import'
2
+
3
+ class Hiera
4
+ module Backend
5
+ module Eyaml
6
+ module Encryptors
7
+ module TwofacUtils
8
+ class Password
9
+
10
+ @@password = nil
11
+
12
+ def self.obtain
13
+
14
+ calling_class = caller[0].split(':').first.split('/').reverse.take(5).join(',')
15
+ raise StandardError "Refusing to supply password" unless calling_class == "twofac.rb,encryptors,eyaml,backend,hiera"
16
+
17
+ return @@password.dup if @@password
18
+ @@password = ask("Please enter your twofactor password: ") {|q| q.echo='*' }
19
+ return @@password.dup
20
+ end
21
+
22
+ end
23
+ end
24
+ end
25
+ end
26
+ end
27
+ end
Binary file
data/tools/regem.sh ADDED
@@ -0,0 +1,17 @@
1
+ #!/bin/bash
2
+
3
+ set -e
4
+
5
+ GEM_NAME="hiera-eyaml-twofac"
6
+
7
+ gem uninstall ${GEM_NAME} --executables
8
+ RAKE_OUT=`rake build`
9
+ VERSION=`echo ${RAKE_OUT} | awk '{print $2}'`
10
+ echo Installing version: ${VERSION} ...
11
+ gem install pkg/${GEM_NAME}-${VERSION}.gem --no-ri --no-rdoc
12
+
13
+ if [ ! -z "$(which eyaml)" ];then
14
+ eyaml version
15
+ else
16
+ echo "install hiera-eyaml to see if gem imports correctly"
17
+ fi
metadata ADDED
@@ -0,0 +1,55 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: hiera-eyaml-twofac
3
+ version: !ruby/object:Gem::Version
4
+ version: '0.1'
5
+ platform: ruby
6
+ authors:
7
+ - Geoff Meakin
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+ date: 2014-11-21 00:00:00.000000000 Z
12
+ dependencies: []
13
+ description: PKCS7 + AES256 2-factor encryptor for use with hiera-eyaml
14
+ email:
15
+ executables: []
16
+ extensions: []
17
+ extra_rdoc_files: []
18
+ files:
19
+ - .gitignore
20
+ - Gemfile
21
+ - Gemfile.lock
22
+ - LICENSE.txt
23
+ - README.md
24
+ - Rakefile
25
+ - hiera-eyaml-twofac.gemspec
26
+ - lib/hiera/backend/eyaml/encryptors/twofac.rb
27
+ - lib/hiera/backend/eyaml/encryptors/twofac/eyaml_init.rb
28
+ - lib/hiera/backend/eyaml/encryptors/twofac_utils/password.rb
29
+ - pkg/hiera-eyaml-twofac-0.1.gem
30
+ - tools/regem.sh
31
+ homepage: http://github.com/gtmtechltd/hiera-eyaml-twofac
32
+ licenses:
33
+ - MIT
34
+ metadata: {}
35
+ post_install_message:
36
+ rdoc_options: []
37
+ require_paths:
38
+ - lib
39
+ required_ruby_version: !ruby/object:Gem::Requirement
40
+ requirements:
41
+ - - '>='
42
+ - !ruby/object:Gem::Version
43
+ version: '0'
44
+ required_rubygems_version: !ruby/object:Gem::Requirement
45
+ requirements:
46
+ - - '>='
47
+ - !ruby/object:Gem::Version
48
+ version: '0'
49
+ requirements: []
50
+ rubyforge_project:
51
+ rubygems_version: 2.0.14
52
+ signing_key:
53
+ specification_version: 4
54
+ summary: Encryption plugin for hiera-eyaml backend for Hiera
55
+ test_files: []