Class: Sentry::AsymmetricSentry

Inherits:
Object
  • Object
show all
Defined in:
lib/sentry/asymmetric_sentry.rb

Constant Summary collapse

@@default_private_key_file =
nil
@@default_public_key_file =
nil
@@default_symmetric_algorithm =
nil
@@CHARS =
('a'..'z').to_a + ('A'..'Z').to_a + ('0'..'9').to_a

Instance Attribute Summary collapse

Class Method Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(options = {}) ⇒ AsymmetricSentry

available options:

  • :private_key_file - encrypted private key file

  • :public_key_file - public key file

  • :symmetric_algorithm - algorithm to use for SymmetricSentry



14
15
16
17
18
19
# File 'lib/sentry/asymmetric_sentry.rb', line 14

def initialize(options = {})
  @public_key = @private_key = nil
  self.private_key_file = options[:private_key_file]
  self.public_key_file  = options[:public_key_file] || @@default_public_key_file
  @symmetric_algorithm = options[:symmetric_algorithm] || @@default_symmetric_algorithm
end

Instance Attribute Details

#private_key_fileObject

Returns the value of attribute private_key_file.



3
4
5
# File 'lib/sentry/asymmetric_sentry.rb', line 3

def private_key_file
  @private_key_file
end

#public_key_fileObject

Returns the value of attribute public_key_file.



4
5
6
# File 'lib/sentry/asymmetric_sentry.rb', line 4

def public_key_file
  @public_key_file
end

#symmetric_algorithmObject

Returns the value of attribute symmetric_algorithm.



5
6
7
# File 'lib/sentry/asymmetric_sentry.rb', line 5

def symmetric_algorithm
  @symmetric_algorithm
end

Class Method Details

.decrypt(data, key = nil) ⇒ Object



121
122
123
# File 'lib/sentry/asymmetric_sentry.rb', line 121

def decrypt(data, key = nil)
  self.new.decrypt(data, key)
end

.decrypt_from_base64(data, key = nil) ⇒ Object



129
130
131
# File 'lib/sentry/asymmetric_sentry.rb', line 129

def decrypt_from_base64(data, key = nil)
  self.new.decrypt_from_base64(data, key)
end

.decrypt_large_from_base64(data, key = nil) ⇒ Object



125
126
127
# File 'lib/sentry/asymmetric_sentry.rb', line 125

def decrypt_large_from_base64(data, key = nil)
   self.new.decrypt_large_from_base64(data, key)
end

.default_private_key_fileObject

cattr_accessor would be lovely



134
135
136
# File 'lib/sentry/asymmetric_sentry.rb', line 134

def default_private_key_file
  @@default_private_key_file
end

.default_private_key_file=(value) ⇒ Object



138
139
140
# File 'lib/sentry/asymmetric_sentry.rb', line 138

def default_private_key_file=(value)
  @@default_private_key_file = value
end

.default_public_key_fileObject



142
143
144
# File 'lib/sentry/asymmetric_sentry.rb', line 142

def default_public_key_file
  @@default_public_key_file
end

.default_public_key_file=(value) ⇒ Object



146
147
148
# File 'lib/sentry/asymmetric_sentry.rb', line 146

def default_public_key_file=(value)
  @@default_public_key_file = value
end

.default_symmetric_algorithmObject



150
151
152
# File 'lib/sentry/asymmetric_sentry.rb', line 150

def default_symmetric_algorithm
  @@default_symmetric_algorithm
end

.default_symmetric_algorithm=(value) ⇒ Object



154
155
156
# File 'lib/sentry/asymmetric_sentry.rb', line 154

def default_symmetric_algorithm=(value)
  @@default_symmetric_algorithm = value
end

.encrypt(data) ⇒ Object



109
110
111
# File 'lib/sentry/asymmetric_sentry.rb', line 109

def encrypt(data)
  self.new.encrypt(data)
end

.encrypt_large_to_base64(data) ⇒ Object



117
118
119
# File 'lib/sentry/asymmetric_sentry.rb', line 117

def encrypt_large_to_base64(data)
  self.new.encrypt_large_to_base64(data)
end

.encrypt_to_base64(data) ⇒ Object



113
114
115
# File 'lib/sentry/asymmetric_sentry.rb', line 113

def encrypt_to_base64(data)
  self.new.encrypt_to_base64(data)
end

.save_random_rsa_key(private_key_file, public_key_file, options = {}) ⇒ Object

  • :key - secret password

  • :symmetric_algorithm - symmetrical algorithm to use



99
100
101
102
103
104
105
106
107
# File 'lib/sentry/asymmetric_sentry.rb', line 99

def save_random_rsa_key(private_key_file, public_key_file, options = {})
  rsa = OpenSSL::PKey::RSA.new(512)
  public_key = rsa.public_key
  private_key = options[:key].to_s.empty? ? 
    rsa.to_s :
    SymmetricSentry.new(:algorithm => options[:symmetric_algorithm]).encrypt_to_base64(rsa.to_s, options[:key])
  File.open(public_key_file, 'w')  { |f| f.write(public_key) }
  File.open(private_key_file, 'w') { |f| f.write(private_key) }
end

Instance Method Details

#chunk_size(padding_length) ⇒ Object



36
37
38
# File 'lib/sentry/asymmetric_sentry.rb', line 36

def chunk_size(padding_length)
  return public_rsa.max_encryptable_length - padding_length
end

#decrypt(data, key = nil) ⇒ Object

Raises:



68
69
70
71
72
# File 'lib/sentry/asymmetric_sentry.rb', line 68

def decrypt(data, key = nil)
  raise NoPrivateKeyError unless private?
  rsa = private_rsa(key)
  return rsa.private_decrypt(data)
end

#decrypt_from_base64(data, key = nil) ⇒ Object



74
75
76
# File 'lib/sentry/asymmetric_sentry.rb', line 74

def decrypt_from_base64(data, key = nil)
  decrypt(Base64.decode64(data), key)
end

#decrypt_large_from_base64(data, key = nil) ⇒ Object

Raises:



27
28
29
30
31
32
33
34
# File 'lib/sentry/asymmetric_sentry.rb', line 27

def decrypt_large_from_base64(data, key=nil)
  raise NoPrivateKeyError unless private?
  chunk_length = public_rsa.max_encryptable_length + 11 # 11 is magic padding for RSA encoding
  b64_decoded = Base64.decode64(data)
  padding_length = b64_decoded[0]
  data = b64_decoded[1, data.length]
  return (0...data.length).step(chunk_length).inject("") { |accum, idx| accum + decrypt_with_padding(data.slice(idx, chunk_length), padding_length, key)}
end

#decrypt_with_padding(data, padding_length, key = nil) ⇒ Object



47
48
49
50
# File 'lib/sentry/asymmetric_sentry.rb', line 47

def decrypt_with_padding(data, padding_length, key=nil)
  decrypted = decrypt(data, key)
  return decrypted[0, decrypted.length - padding_length]
end

#encrypt(data) ⇒ Object

Raises:



21
22
23
24
25
# File 'lib/sentry/asymmetric_sentry.rb', line 21

def encrypt(data)
  raise NoPublicKeyError unless public?
  rsa = public_rsa
  return rsa.public_encrypt(data)
end

#encrypt_large_to_base64(data) ⇒ Object

Raises:



40
41
42
43
44
45
# File 'lib/sentry/asymmetric_sentry.rb', line 40

def encrypt_large_to_base64(data)
  raise NoPublicKeyError unless public?
  padding_length = 8
  chunk_length = chunk_size(padding_length)
  return Base64.encode64(padding_length.chr + (0...data.length).step(chunk_length).inject("") {|accum, idx| accum + encrypt_with_padding( data.slice(idx, chunk_length), padding_length)} )
end

#encrypt_to_base64(data) ⇒ Object



64
65
66
# File 'lib/sentry/asymmetric_sentry.rb', line 64

def encrypt_to_base64(data)
  Base64.encode64(encrypt(data))
end

#encrypt_with_padding(data, padding_length) ⇒ Object



52
53
54
# File 'lib/sentry/asymmetric_sentry.rb', line 52

def encrypt_with_padding(data, padding_length)
  encrypt(data + rand_string(padding_length))
end

#private?Boolean

Returns:

  • (Boolean)


91
92
93
94
# File 'lib/sentry/asymmetric_sentry.rb', line 91

def private?
  return true unless @private_key.nil?
  load_private_key and return @private_key
end

#public?Boolean

Returns:

  • (Boolean)


86
87
88
89
# File 'lib/sentry/asymmetric_sentry.rb', line 86

def public?
  return true unless @public_key.nil?
  load_public_key and return @public_key
end

#rand_string(length = 8) ⇒ Object



58
59
60
61
62
# File 'lib/sentry/asymmetric_sentry.rb', line 58

def rand_string(length=8)
  s=''
  length.times{ s << @@CHARS[rand(@@CHARS.length)] }
  s
end