mongrel_crypted_download 0.4 → 0.5

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.
data/Rakefile CHANGED
@@ -15,7 +15,7 @@ setup_rdoc ['README', 'LICENSE', 'COPYING', 'lib/**/*.rb', 'doc/**/*.rdoc']
15
15
  desc "Does a full compile, test run"
16
16
  task :default => [:test, :package]
17
17
 
18
- version="0.4"
18
+ version="0.5"
19
19
  name="mongrel_crypted_download"
20
20
 
21
21
  setup_gem(name, version) do |spec|
@@ -0,0 +1,313 @@
1
+ require "ezcrypto.rb"
2
+ module ActiveCrypto # :nodoc:
3
+
4
+ def self.append_features(base) #:nodoc:
5
+ super
6
+ base.extend(ClassMethods)
7
+ end
8
+
9
+ =begin rdoc
10
+
11
+ Usage is very simple. You will generally only need the two class methods listed here in your ActiveRecord class model.
12
+
13
+ == License
14
+
15
+ ActiveCrypto and EzCrypto are released under the MIT license.
16
+
17
+
18
+ == Support
19
+
20
+ To contact the author, send mail to pelleb@gmail.com
21
+
22
+ Also see my blogs at:
23
+ http://stakeventures.com and
24
+ http://neubia.com
25
+
26
+ This project was based on code used in my project StakeItOut, where you can securely share web services with your partners.
27
+ https://stakeitout.com
28
+
29
+ (C) 2005 Pelle Braendgaard
30
+
31
+ =end
32
+ module ClassMethods
33
+ @@session_keys={}
34
+
35
+ =begin rdoc
36
+ Turn encryption on for this record. List all encrypted attributes
37
+
38
+ class Document < ActiveRecord::Base
39
+ encrypt :title,:body
40
+ end
41
+
42
+ Include optional option :key, to specify an external KeyHolder, which holds the key used for encrypting and decrypting:
43
+
44
+ class Document < ActiveRecord::Base
45
+ belongs_to :user
46
+ encrypt :title,:body,:key=>:user
47
+ end
48
+
49
+ =end
50
+ def encrypt(*attributes)
51
+ include ActiveCrypto::Encrypted
52
+ before_save :encrypt_attributes
53
+ after_save :decrypt_attributes
54
+ options=attributes.last.is_a?(Hash) ? attributes.pop : {}
55
+ keyholder
56
+ if options and options[:key]
57
+ module_eval <<-"end;"
58
+ def session_key
59
+ (send :#{options[:key]} ).send :session_key
60
+ end
61
+ @@external_key=true
62
+ end;
63
+ end
64
+ self.encrypted_attributes=attributes
65
+ end
66
+
67
+ =begin rdoc
68
+ Creates support in this class for holding a key. Adds the following methods:
69
+
70
+ * enter_password(password,salt="onetwothree")
71
+ * set_session_key(key)
72
+ * session_key
73
+
74
+ Use it as follows:
75
+
76
+ class User < ActiveRecord::Base
77
+ has_many :documents
78
+ keyholder
79
+ end
80
+
81
+ =end
82
+ def keyholder()
83
+ include ActiveCrypto::AssociationKeyHolder
84
+ after_create :save_session_key
85
+ end
86
+
87
+ =begin rdoc
88
+ Clears the session_key array. Generally this is handled automatically as a filter in ActionController. Only use these if you need to
89
+ do something out of the ordinary.
90
+ =end
91
+ def clear_session_keys() #:nodoc:
92
+ @@session_keys.clear
93
+ end
94
+
95
+ =begin rdoc
96
+ Sets the session_keys array. Only use these if you need to
97
+ do something out of the ordinary, as it is handled
98
+ =end
99
+ def session_keys=(keys) #:nodoc:
100
+ @@session_keys=keys
101
+ end
102
+
103
+ def session_keys() #:nodoc:
104
+ @@session_keys
105
+ end
106
+
107
+ end
108
+
109
+ =begin rdoc
110
+ This module handles all standard key management features.
111
+ =end
112
+ module KeyHolder
113
+
114
+ =begin rdoc
115
+ Creates a key for object based on given password and an optional salt.
116
+ =end
117
+ def enter_password(password,salt="onetwothree")
118
+ set_session_key(EzCrypto::Key.with_password(password, salt))
119
+ end
120
+
121
+ =begin rdoc
122
+ Decodes the Base64 encoded key and uses it as it's session key
123
+ =end
124
+ def set_encoded_key(enc)
125
+ set_session_key(EzCrypto::Key.decode(enc))
126
+ end
127
+ =begin rdoc
128
+ Sets a session key for the object. This should be a EzCrypto::Key instance.
129
+ =end
130
+ def set_session_key(key)
131
+ @session_key=key
132
+ self.decrypt_attributes if self.class.include? Encrypted
133
+ end
134
+
135
+ =begin rdoc
136
+ Returns the session_key
137
+ =end
138
+ def session_key
139
+ @session_key
140
+ end
141
+
142
+ end
143
+
144
+ module AssociationKeyHolder
145
+ include ActiveCrypto::KeyHolder
146
+
147
+
148
+ def save_session_key
149
+ ActiveRecord::Base.session_keys[session_key_id]=@session_key if @session_key
150
+ end
151
+ =begin rdoc
152
+ Sets a session key for the object. This should be a EzCrypto::Key instance.
153
+ =end
154
+ def set_session_key(key)
155
+ if self.new_record?
156
+ @session_key=key
157
+ else
158
+ ActiveRecord::Base.session_keys[session_key_id]=key
159
+ end
160
+ decrypt_attributes if self.class.include? Encrypted #if respond_to?(:decrypt_attributes)
161
+
162
+ end
163
+
164
+ =begin rdoc
165
+ Returns the session_key
166
+ =end
167
+ def session_key
168
+ if self.new_record?
169
+ @session_key
170
+ else
171
+ ActiveRecord::Base.session_keys[session_key_id]
172
+ end
173
+ end
174
+
175
+
176
+
177
+ def session_key_id
178
+ "#{self.class.to_s}:#{id}"
179
+ end
180
+
181
+ end
182
+
183
+ module Encrypted #:nodoc:
184
+ def self.append_features(base) #:nodoc:
185
+ super
186
+ base.extend ClassAccessors
187
+ end
188
+
189
+ module ClassAccessors
190
+ def encrypted_attributes
191
+ @encrypted_attributes||=[]
192
+ end
193
+
194
+ def encrypted_attributes=(attrs)
195
+ @encrypted_attributes=attrs
196
+ end
197
+
198
+ end
199
+
200
+ protected
201
+
202
+ def encrypt_attributes
203
+ if !is_encrypted?
204
+ self.class.encrypted_attributes.each do |key|
205
+ value=read_attribute(key)
206
+ write_attribute(key,_encrypt(value)) if value
207
+ end
208
+ @is_encrypted=true
209
+ end
210
+ true
211
+ end
212
+
213
+ def decrypt_attributes
214
+ if is_encrypted?
215
+ self.class.encrypted_attributes.each do |key|
216
+ value=read_attribute(key)
217
+ write_attribute(key,_decrypt(value)) if value
218
+ end
219
+ @is_encrypted=false
220
+ end
221
+ true
222
+ end
223
+
224
+ def after_find
225
+ @is_encrypted=true
226
+ decrypt_attributes unless session_key.nil?
227
+ end
228
+
229
+ private
230
+ def is_encrypted?
231
+ @is_encrypted
232
+ end
233
+
234
+ def _decrypt(data)
235
+ if session_key.nil?
236
+ raise MissingKeyError
237
+ else
238
+ if data
239
+ session_key.decrypt(data)
240
+ else
241
+ nil
242
+ end
243
+ end
244
+ end
245
+
246
+ def _encrypt(data)
247
+ if session_key.nil?
248
+ raise MissingKeyError
249
+ else
250
+ if data
251
+ session_key.encrypt(data)
252
+ else
253
+ nil
254
+ end
255
+ end
256
+ end
257
+
258
+ end
259
+
260
+
261
+ module ActionController # :nodoc:
262
+ =begin rdoc
263
+ This includes some basic support in the ActionController for handling session keys. It creates two filters one before the action and one after.
264
+ These do the following:
265
+
266
+ If the users session already has a 'session_keys' value it loads it into the ActiveRecord::Base.session_keys class field. If not it
267
+ clears any existing session_keys.
268
+
269
+ Leaving the action it stores any session_keys in the corresponding session variable.
270
+
271
+ These filters are automatically enabled. You do not have to do anything.
272
+
273
+ To manually clear the session keys call clear_session_keys. This should be done for example as part of a session log off action.
274
+ =end
275
+ def self.append_features(base) #:nodoc:
276
+ super
277
+ base.send :prepend_before_filter, :load_session_keys
278
+ base.send :prepend_after_filter, :save_session_keys
279
+ end
280
+
281
+ =begin rdoc
282
+ Clears the session keys. Call this when a user logs of.
283
+ =end
284
+ def clear_session_keys
285
+ ActiveRecord::Base.clear_session_keys
286
+ end
287
+
288
+
289
+ private
290
+ def load_session_keys
291
+ if session['session_keys']
292
+ ActiveRecord::Base.session_keys=session['session_keys']
293
+ else
294
+ ActiveRecord::Base.clear_session_keys
295
+ end
296
+ end
297
+
298
+ def save_session_keys
299
+ if ActiveRecord::Base.session_keys.size>0
300
+ session['session_keys']=ActiveRecord::Base.session_keys
301
+ else
302
+ session['session_keys']=nil
303
+ end
304
+ end
305
+
306
+
307
+ end
308
+
309
+ class MissingKeyError < RuntimeError
310
+ end
311
+ end
312
+ #ActiveRecord::Base.send :include, ActiveCrypto
313
+ #ActionController::Base.send :include, ActiveCrypto::ActionController
data/lib/ezcrypto.rb ADDED
@@ -0,0 +1,592 @@
1
+ require 'openssl'
2
+ require 'digest/sha2'
3
+ require 'digest/sha1'
4
+ require 'base64'
5
+
6
+ module EzCrypto #:nodoc:
7
+
8
+
9
+ =begin rdoc
10
+ The Key is the only class you need to understand for simple use.
11
+
12
+ === Algorithms
13
+
14
+ The crypto algorithms default to aes-128-cbc however on any of the class methods you can change it to one of the standard openssl cipher names using the
15
+ optional <tt>:algorithm=>alg name</tt> parameter.
16
+
17
+ Eg.
18
+ Key.new @raw, :algorithm=>"des"
19
+ Key.generate :algorithm=>"blowfish"
20
+ Key.with_password @pwd,@salt,:algorithm=>"aes256"
21
+
22
+
23
+ == License
24
+
25
+ ActiveCrypto and EzCrypto are released under the MIT license.
26
+
27
+
28
+ == Support
29
+
30
+ To contact the author, send mail to pelleb@gmail.com
31
+
32
+ Also see my blogs at:
33
+ http://stakeventures.com and
34
+ http://neubia.com
35
+
36
+ This project was based on code used in my project StakeItOut, where you can securely share web services with your partners.
37
+ https://stakeitout.com
38
+
39
+ (C) 2005 Pelle Braendgaard
40
+
41
+ =end
42
+
43
+ class Key
44
+
45
+ attr_reader :raw, :algorithm
46
+
47
+ @@block_size = 512
48
+
49
+ =begin rdoc
50
+ Set the block-size for IO-operations (default: 512 bytes)
51
+ =end
52
+ def self.block_size=(size)
53
+ @@block_size = size
54
+ end
55
+
56
+ =begin rdoc
57
+ Return the block-size for IO-operations.
58
+ =end
59
+ def self.block_size
60
+ @@block_size
61
+ end
62
+
63
+
64
+ =begin rdoc
65
+ Initialize the key with raw unencoded binary key data. This needs to be at least
66
+ 16 bytes long for the default aes-128 algorithm.
67
+ =end
68
+ def initialize(raw,options = {})
69
+ @raw=raw
70
+ @algorithm=options[:algorithm]||"aes-128-cbc"
71
+ end
72
+
73
+ =begin rdoc
74
+ Generate random key.
75
+ =end
76
+ def self.generate(options = {})
77
+ Key.new(EzCrypto::Digester.generate_key(calculate_key_size(options[:algorithm])),options)
78
+ end
79
+
80
+ =begin rdoc
81
+ Create key generated from the given password and salt
82
+ =end
83
+ def self.with_password(password,salt,options = {})
84
+ Key.new(EzCrypto::Digester.get_key(password,salt,calculate_key_size(options[:algorithm])),options)
85
+ end
86
+
87
+ =begin rdoc
88
+ Initialize the key with Base64 encoded key data.
89
+ =end
90
+ def self.decode(encoded,options = {})
91
+ Key.new(Base64.decode64(encoded),options)
92
+ end
93
+
94
+ =begin rdoc
95
+ Encrypts the data with the given password and a salt. Short hand for:
96
+
97
+ key=Key.with_password(password,salt,options)
98
+ key.encrypt(data)
99
+
100
+ =end
101
+ def self.encrypt_with_password(password,salt,data,options = {})
102
+ key=Key.with_password(password,salt,options)
103
+ key.encrypt(data)
104
+ end
105
+
106
+ =begin rdoc
107
+ Decrypts the data with the given password and a salt. Short hand for:
108
+
109
+ key=Key.with_password(password,salt,options)
110
+ key.decrypt(data)
111
+
112
+
113
+ =end
114
+ def self.decrypt_with_password(password,salt,data,options = {})
115
+ key=Key.with_password(password,salt,options)
116
+ key.decrypt(data)
117
+ end
118
+
119
+ =begin rdoc
120
+ Given an algorithm this calculates the keysize. This is used by both
121
+ the generate and with_password methods. This is not yet 100% complete.
122
+ =end
123
+ def self.calculate_key_size(algorithm)
124
+ if !algorithm.nil?
125
+ algorithm=~/^([[:alnum:]]+)(-(\d+))?/
126
+ if $3
127
+ size=($3.to_i)/8
128
+ else
129
+ case $1
130
+ when "bf"
131
+ size = 16
132
+ when "blowfish"
133
+ size = 16
134
+ when "des"
135
+ size = 8
136
+ when "des3"
137
+ size = 24
138
+ when "aes128"
139
+ size = 16
140
+ when "aes192"
141
+ size = 24
142
+ when "aes256"
143
+ size = 32
144
+ when "rc2"
145
+ size = 16
146
+ when "rc4"
147
+ size = 16
148
+ else
149
+ size = 16
150
+ end
151
+ end
152
+ end
153
+ if size.nil?
154
+ size = 16
155
+ end
156
+
157
+ size
158
+ end
159
+
160
+ =begin rdoc
161
+ returns the Base64 encoded key.
162
+ =end
163
+ def encode
164
+ Base64.encode64(@raw).chop
165
+ end
166
+
167
+ =begin rdoc
168
+ returns the Base64 encoded key. Synonym for encode.
169
+ =end
170
+ def to_s
171
+ encode
172
+ end
173
+
174
+ =begin rdoc
175
+ Encrypts the data and returns it in encrypted binary form.
176
+ =end
177
+ def encrypt(data)
178
+ if data==nil || data==""
179
+ nil
180
+ else
181
+ encrypter("")
182
+ @cipher.encrypt(data)
183
+ end
184
+ end
185
+
186
+ =begin rdoc
187
+ Encrypts the data and returns it in encrypted Base64 encoded form.
188
+ =end
189
+ def encrypt64(data)
190
+ Base64.encode64(encrypt(data))
191
+ end
192
+
193
+ =begin rdoc
194
+ Decrypts the data passed to it in binary format.
195
+ =end
196
+ def decrypt(data)
197
+ if data==nil || data==""
198
+ nil
199
+ else
200
+ decrypter("")
201
+ @cipher.gulp(data)
202
+ end
203
+ # rescue
204
+ # puts @algorithm
205
+ # puts self.encode
206
+ # puts data.size
207
+ # throw $!
208
+ end
209
+
210
+ =begin rdoc
211
+ Decrypts a Base64 formatted string
212
+ =end
213
+ def decrypt64(data)
214
+ decrypt(Base64.decode64(data))
215
+ end
216
+
217
+ =begin rdoc
218
+ Allows keys to be marshalled
219
+ =end
220
+ def marshal_dump
221
+ "#{self.algorithm}$$$#{self.encode}"
222
+ end
223
+
224
+ =begin rdoc
225
+ Allows keys to be unmarshalled
226
+ =end
227
+ def marshal_load(s)
228
+ a, r = s.split '$$$'
229
+ @algorithm = a
230
+ @raw = Base64.decode64(r)
231
+ end
232
+
233
+ =begin rdoc
234
+ Create a file with minimal permissions, and yield
235
+ it to a block. By default only the owner may read it.
236
+ =end
237
+ def safe_create(file, mod=0400, mask=0066)
238
+ begin
239
+ old_umask = File.umask
240
+ File.umask(mask)
241
+ File.open(file, File::CREAT | File::EXCL | File::WRONLY) do |f|
242
+ yield(f) if block_given?
243
+ end
244
+ ensure
245
+ File.umask(old_umask)
246
+ end
247
+ File.chmod(mod, file) if File.exists?(file)
248
+ File.size(file)
249
+ end
250
+
251
+
252
+ =begin rdoc
253
+ Overwrite a file with zero values before removing it's filesystem inode.
254
+ This is not very safe :-)
255
+ =end
256
+ def safe_delete(file)
257
+ begin
258
+ to_clear = File.size(file)
259
+ zeroes = Array.new(Key.block_size, "\0").join
260
+ File.chmod(0600, file)
261
+ File.open(file, File::WRONLY) do |f|
262
+ f.rewind
263
+ while to_clear > 0
264
+ f.write(zeroes)
265
+ to_clear -= Key.block_size
266
+ end
267
+ f.flush
268
+ end
269
+ ensure
270
+ File.delete(file) if File.exists?(file)
271
+ end
272
+ return !File.exists?(file)
273
+ end
274
+
275
+
276
+ =begin rdoc
277
+ Open a file readonly and yield it to a block.
278
+ =end
279
+ def safe_read(file)
280
+ File.open(file, File::RDONLY) do |i|
281
+ yield(i) if block_given?
282
+ end
283
+ end
284
+
285
+ private :safe_create, :safe_read, :safe_delete
286
+
287
+ =begin rdoc
288
+ Load a key from a yaml_file generated via Key#store.
289
+ =end
290
+ def self.load(filename)
291
+ require 'yaml'
292
+ hash = YAML::load_file(filename)
293
+ req = proc { |k| hash[k] or raise "Missing element #{k} in #{filename}" }
294
+ key = self.new Base64.decode64(req.call(:key)) , :algorithm => req.call(:algorithm)
295
+ return key
296
+ end
297
+
298
+
299
+ =begin rdoc
300
+ Save the key data into a file, try to do this in a secure manner.
301
+ NOTE: YAML::store & friends are not used to encance control over
302
+ the generated file format.
303
+ =end
304
+ def store(filename)
305
+ safe_create(filename) do |f|
306
+ selfenc = self.encode
307
+ f.puts "---"
308
+ f.puts ":EZCRYPTO KEY FILE: KEEP THIS SECURE !"
309
+ f.puts ":created: #{Time.now}"
310
+ f.puts ":algorithm: #{@algorithm}"
311
+ f.puts ":key: #{selfenc}"
312
+ end
313
+ end
314
+
315
+
316
+ =begin rdoc
317
+ Get a Encrypter object. You have to call #final on it by yourself!
318
+ =end
319
+ def encrypter(target='')
320
+ @cipher = EzCrypto::Encrypter.new(self,target,@algorithm)
321
+ end
322
+
323
+
324
+ =begin rdoc
325
+ Get a Decrypter object. You have to call #final on it by yourself!
326
+ =end
327
+ def decrypter(target='')
328
+ @cipher = EzCrypto::Decrypter.new(self,target,@algorithm)
329
+ end
330
+
331
+ =begin rdoc
332
+ Create a Decrypter object and yield it to a block.
333
+ You must *not* call #final by yourself, the method
334
+ does this.
335
+ =end
336
+ def on_decrypter(target='', &block)
337
+ decrypter(target)
338
+ on_cipher(&block)
339
+ end
340
+
341
+ =begin rdoc
342
+ Create an Encrypter object and yield it to a block.
343
+ You must *not* call #final by yourself, the method
344
+ does this.
345
+ =end
346
+ def on_encrypter(target='', &block)
347
+ encrypter(target)
348
+ on_cipher(&block)
349
+ end
350
+
351
+
352
+ =begin rdoc
353
+ Helper method, yields the current cipher to a block.
354
+ =end
355
+ def on_cipher(&block)
356
+ begin
357
+ block.call @cipher
358
+ ensure
359
+ @cipher.final
360
+ end
361
+ end
362
+
363
+ private :on_cipher
364
+
365
+
366
+ =begin rdoc
367
+ Encrypt a file 'inplace' and add a suffix
368
+ see #cipher_file.
369
+ IMPORTANT: The inputfile will be deleted by default.
370
+ =end
371
+ def encrypt_file(src, tgt=nil, options = {} )
372
+ options = { :suffix => '.ez', :autoclean => 'true' }.update(options)
373
+ tgt = "#{src}#{options[:suffix]}" unless tgt
374
+ cipher_file :on_encrypter, src, tgt, options[:autoclean]
375
+ end
376
+
377
+
378
+ =begin rdoc
379
+ Decrypt a file 'inplace' and remove a suffix
380
+ see #cipher_file
381
+ IMPORTANT: The inputfile will be deleted by default.
382
+ =end
383
+ def decrypt_file(src, tgt=nil, options = {} )
384
+ options = { :suffix => '.ez', :autoclean => 'true' }.update(options)
385
+ unless tgt
386
+ tgt = src
387
+ tgt = tgt.gsub(/#{options[:suffix]}$/, '')
388
+ end
389
+ cipher_file :on_decrypter, src, tgt, options[:autoclean]
390
+ end
391
+
392
+
393
+ =begin rdoc
394
+ uses either #on_decrypter or #on_encrypter to transform a given sourcefile
395
+ to a targetfile. the sourcefile is deleted after sucessful transformation
396
+ the delete_source is 'true'.
397
+ =end
398
+ def cipher_file(method, sourcefile, targetfile, delete_source)
399
+ raise(ArgumentError, "source == target #{sourcefile}") if sourcefile == targetfile
400
+ safe_create(targetfile,0600) do |o|
401
+ self.send(method, o) do |c|
402
+ safe_read(sourcefile) do |i|
403
+ loop do
404
+ buffer = i.read(Key.block_size) or break
405
+ c << buffer
406
+ end
407
+ end
408
+ end
409
+ end
410
+ safe_delete(sourcefile) if delete_source && File.exists?(targetfile)
411
+ return targetfile
412
+ end
413
+
414
+ private :cipher_file
415
+
416
+ end
417
+
418
+ =begin rdoc
419
+ Abstract Wrapper around OpenSSL's Cipher object. Extended by Encrypter and Decrypter.
420
+
421
+ You probably should be using the Key class instead.
422
+
423
+ Warning! The interface may change.
424
+
425
+ =end
426
+ class CipherWrapper #:nodoc:
427
+
428
+ =begin rdoc
429
+
430
+ =end
431
+ def initialize(key,target,mode,algorithm)
432
+ @cipher = OpenSSL::Cipher::Cipher.new(algorithm)
433
+ if mode
434
+ @cipher.encrypt
435
+ else
436
+ @cipher.decrypt
437
+ end
438
+ @cipher.key=key.raw
439
+ @cipher.padding=1
440
+ @target=target
441
+ @finished=false
442
+ end
443
+
444
+
445
+ def to_target(data)
446
+ return data
447
+ end
448
+
449
+ =begin rdoc
450
+ Process the givend data with the cipher.
451
+ =end
452
+ def update(data)
453
+ reset if @finished
454
+ @target<< to_target(@cipher.update(data))
455
+ end
456
+
457
+ =begin rdoc
458
+
459
+ =end
460
+ def <<(data)
461
+ update(data)
462
+ end
463
+
464
+ =begin rdoc
465
+ Finishes up any last bits of data in the cipher and returns the final result.
466
+ =end
467
+ def final
468
+ @target<< to_target(@cipher.final)
469
+ @finished=true
470
+ @target
471
+ end
472
+
473
+ =begin rdoc
474
+ Processes the entire data string using update and performs a final on it returning the data.
475
+ =end
476
+ def gulp(data)
477
+ update(data)
478
+ final
479
+ # rescue
480
+ # breakpoint
481
+ end
482
+
483
+ =begin rdoc
484
+
485
+ =end
486
+ def reset(target="")
487
+ @target=target
488
+ @finished=false
489
+ end
490
+ end
491
+
492
+ =begin rdoc
493
+ Wrapper around OpenSSL Cipher for Encryption use.
494
+
495
+ You probably should be using Key instead.
496
+
497
+ Warning! The interface may change.
498
+
499
+ =end
500
+ class Encrypter<EzCrypto::CipherWrapper #:nodoc:
501
+
502
+ =begin rdoc
503
+
504
+ =end
505
+ def initialize(key,target="",algorithm="aes-128-cbc")
506
+ super(key,target,true,algorithm)
507
+ end
508
+
509
+ =begin rdoc
510
+
511
+ =end
512
+ def encrypt(data)
513
+ gulp(data)
514
+ end
515
+ end
516
+
517
+ =begin rdoc
518
+ Wrapper around OpenSSL Cipher for Decryption use.
519
+
520
+ You probably should be using Key instead.
521
+
522
+ Warning! The interface may change.
523
+ =end
524
+ class Decrypter<EzCrypto::CipherWrapper #:nodoc:
525
+ =begin rdoc
526
+
527
+ =end
528
+ def initialize(key,target="",algorithm="aes-128-cbc")
529
+ super(key,target,false,algorithm)
530
+ end
531
+
532
+ =begin rdoc
533
+
534
+ =end
535
+ def decrypt(data)
536
+ gulp(data)
537
+ end
538
+ end
539
+
540
+ =begin rdoc
541
+
542
+ =end
543
+ class Digester
544
+ =begin rdoc
545
+ Various handy Digest methods.
546
+
547
+ Warning! The interface may change.
548
+ =end
549
+ def self.get_key(password,salt,size)
550
+ digest(salt+password,size)
551
+ end
552
+
553
+ =begin rdoc
554
+
555
+ =end
556
+ def self.generate_key(size=16)
557
+ key=OpenSSL::Random.random_bytes(size)
558
+ digest(key,size)
559
+ end
560
+
561
+ =begin rdoc
562
+
563
+ =end
564
+ def self.generate_key64(size=32)
565
+ key=OpenSSL::Random.random_bytes(size)
566
+ digest(key,size)
567
+ end
568
+
569
+ =begin rdoc
570
+
571
+ =end
572
+ def self.digest(data,size=16)
573
+ if size==0
574
+ ""
575
+ elsif size<=16
576
+ Digest::SHA1.digest(data)[0..(size-1)]
577
+ else
578
+ Digest::SHA256.digest(data)[0..(size-1)]
579
+ end
580
+ end
581
+
582
+ =begin rdoc
583
+
584
+ =end
585
+ def self.digest64(data)
586
+ Base64.encode64(digest(data))
587
+ end
588
+ end
589
+
590
+ end
591
+
592
+