encrypted_text 0.1.1 → 0.1.2

Sign up to get free protection for your applications and to get access to all the features.
data/README.md CHANGED
@@ -1,12 +1,15 @@
1
1
  encrypted_text
2
2
  ==============
3
3
 
4
- Password-based, two-way encryption with string output. Uses AES encryption
4
+ Password-based, two-way encryption with string output. Uses AES encryption.
5
5
 
6
6
  Usage example
7
7
  -------------
8
8
 
9
- In order to encode or decode a message, you should know the **key** and **signature** ahead of time. The key is a 16-, 24-, or 32-character string used for AES encryption key. The signature is prepended to the message before encryption, and verified after decryption.
9
+ In order to encode or decode a message, you should know the **key** and **signature** ahead of time.
10
+
11
+ - The key is a 16-, 24-, or 32-character string, used as an AES encryption key.
12
+ - The signature is prepended to the message before encryption, and verified after decryption.
10
13
 
11
14
  ```ruby
12
15
  require 'encrypted_text'
@@ -20,7 +23,7 @@ encoded = codec.encode("Hello, world!")
20
23
  original_message = codec.decode(encoded)
21
24
  ```
22
25
 
23
- You can also add a random seed, so that repeated encodings of the same message produce different results.
26
+ You can also add a random salt, so that repeated encodings of the same message produce different results.
24
27
 
25
28
  ```ruby
26
29
  # Continued from previous example
@@ -34,6 +37,6 @@ b = codec.encode(message) # Should be a different result!
34
37
  Motivation
35
38
  ----------
36
39
 
37
- I wrote this library so I could generate tokens that encoded actual information, but seemed opaque and pseudo-random to the outside world.
40
+ Among other things, this library is useful for generating tokens that seem opaque to the outside world, but actually encode real information.
38
41
 
39
- In situations where tokens are passed from a service to an outside party and then back again, the service needs some way of resolving tokens passed back to it. Oftentimes this means performing a lookup on a stored mapping (e.g. a database query) between the token and some kind of cleartext data that outside parties never see. But this comes with all the clumsiness of maintaining and interacting with a persistent data store. For some applications, it might be acceptable simply to encode data directly into the token itself, using a secret that only the originating service has access to. EncryptedText provides a simple API to accomplish this.
42
+ For example, in situations where tokens are passed from a service to an outside party and then back again, the service needs some way of resolving tokens passed back to it. Oftentimes this means performing a lookup on a stored mapping (e.g. a database query) between the token and some kind of cleartext data that outside parties never see. But this comes with all the clumsiness of maintaining and interacting with a persistent data store. For some applications, it might be acceptable simply to encode data directly into the token itself, using a secret that only the originating service has access to. EncryptedText provides a simple API to accomplish this.
@@ -11,11 +11,10 @@ module EncryptedText
11
11
  attr_reader :charset, :key, :salt_size
12
12
 
13
13
  KEY_CHAR_SIZES = [16, 24, 32] # An AES key must be 8-bit char strings of these lengths
14
- DEFAULT_CHARSET = Array('A'..'Z') + Array('a'..'z') + Array('0'..'9') + [ '-', '_' ] # base 64, URL-safe
14
+ SALT_CHARSET = Array(32..126).map{ |i| i.chr } # Printable ASCII chars go from 32 to 126
15
15
 
16
16
  def initialize(opts)
17
17
  config = {
18
- :charset => DEFAULT_CHARSET,
19
18
  :signature => '',
20
19
  :key => nil,
21
20
  :salt_size => 0,
@@ -28,18 +27,9 @@ module EncryptedText
28
27
  end
29
28
  end
30
29
 
31
- def charset=(charset)
32
- @charset = charset
33
- @reverse_charset = @charset.each.with_index.reduce({}) do |res, (c, i)|
34
- res[c] = i
35
- res
36
- end
37
- end
38
-
39
30
  def key=(key)
31
+ @engine = FastAES.new(key)
40
32
  @key = key
41
- @engine = FastAES.new(@key)
42
- @key
43
33
  end
44
34
 
45
35
  def salt_size=(s)
@@ -47,18 +37,9 @@ module EncryptedText
47
37
  @salt_size = s
48
38
  end
49
39
 
50
- def base_encode(val, from_base)
51
- val.b(from_base).to_a.map{ |id| @charset[id] }.join
52
- end
53
-
54
- def base_decode(val)
55
- val.split.map{ |c| @reverse_charset.fetch(c) }.b(@charset.size).to_i
56
- end
57
-
58
40
  def encode(message)
59
- salt = (0...@salt_size).map { @charset.sample }.join
60
- signed = @signature + salt + message
61
- encrypted = @engine.encrypt(signed)
41
+ signed_and_salted = @signature + random_salt + message
42
+ encrypted = @engine.encrypt(signed_and_salted)
62
43
  hex_string = '1' + encrypted.to_hex_string.split(' ').join # Add "1" prefix in case hex_string has leading zeroes
63
44
  encoded = Radix.convert(hex_string.upcase, 16, 62) # Radix requires allcaps
64
45
  end
@@ -69,16 +50,20 @@ module EncryptedText
69
50
  hex_string = hex_string[1..-1] if hex_string[0] == '1' # remove "1" prefix
70
51
  hex_string = "0" + hex_string if (hex_string.size % 2) != 0 # Make sure we have an even number of hex digits
71
52
  byte_string = hex_string.to_byte_string
72
- decrypted = @engine.decrypt(hex_string.to_byte_string)
53
+ decrypted = @engine.decrypt(byte_string)
73
54
  rescue #TODO: don't use generic rescue here
74
55
  raise EncryptedText::Err::CannotDecrypt
75
56
  end
76
57
 
77
58
  # Ensure that the message is signed correctly
78
- matches = decrypted.match(/^#{Regexp.escape(signature)}(.+)/)
79
- raise EncryptedText::Err::BadSignature unless matches
80
- salted_message = matches[1]
81
- message = salted_message[@salt_size..-1]
59
+ raise EncryptedText::Err::BadSignature unless decrypted.index(@signature) == 0
60
+
61
+ # Remove signature and salt
62
+ decrypted[(@signature.size + @salt_size)..-1]
63
+ end
64
+
65
+ def random_salt
66
+ (0...@salt_size).map{ SALT_CHARSET.sample }.join
82
67
  end
83
68
 
84
69
  end
@@ -1,3 +1,3 @@
1
1
  module EncryptedText
2
- VERSION = '0.1.1'
2
+ VERSION = '0.1.2'
3
3
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: encrypted_text
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.1
4
+ version: 0.1.2
5
5
  prerelease:
6
6
  platform: ruby
7
7
  authors:
@@ -9,7 +9,7 @@ authors:
9
9
  autorequire:
10
10
  bindir: bin
11
11
  cert_chain: []
12
- date: 2012-09-12 00:00:00.000000000 Z
12
+ date: 2012-09-13 00:00:00.000000000 Z
13
13
  dependencies:
14
14
  - !ruby/object:Gem::Dependency
15
15
  name: fast-aes