Class: Reedb::SecureHash
- Inherits:
-
Object
- Object
- Reedb::SecureHash
- Defined in:
- lib/reedb/security/secure_hash.rb
Constant Summary collapse
- PBKDF2_ITERATIONS =
Constants for the hashing process. Can be changed without breaking existing hashes!
10000
- SALT_BYTE_SIZE =
32
- HASH_BYTE_SIZE =
24
- HASH_SECTIONS =
3
- SECTION_DELIMITER =
'::'
- ITERATIONS_INDEX =
0
- SALT_INDEX =
1
- HASH_INDEX =
2
Class Method Summary collapse
- .assert(truth, msg) ⇒ Object
-
.runSelfTests ⇒ Object
Run tests to ensure the module is functioning properly.
- .secure_hash(password) ⇒ Object
-
.validate_pw(password, correctHash) ⇒ Object
Checks if a password is correct given a hash of the correct one.
Class Method Details
.assert(truth, msg) ⇒ Object
122 123 124 125 126 127 128 129 |
# File 'lib/reedb/security/secure_hash.rb', line 122 def self.assert( truth, msg ) if truth puts "PASS [#{msg}]" else puts "FAIL [#{msg}]" @@allPass = false end end |
.runSelfTests ⇒ Object
Run tests to ensure the module is functioning properly. Returns true if all tests succeed, false if not.
94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 |
# File 'lib/reedb/security/secure_hash.rb', line 94 def self.runSelfTests puts "Sample hashes:" 3.times { puts secure_hash("password") } puts "\nRunning self tests..." @@allPass = true correctPassword = 'aaaaaaaaaa' wrongPassword = 'aaaaaaaaab' hash = secure_hash(correctPassword) assert( validate_pw( correctPassword, hash ) == true, "correct password" ) assert( validate_pw( wrongPassword, hash ) == false, "wrong password" ) h1 = hash.split( SECTION_DELIMITER ) h2 = secure_hash( correctPassword ).split( SECTION_DELIMITER ) assert( h1[HASH_INDEX] != h2[HASH_INDEX], "different hashes" ) assert( h1[SALT_INDEX] != h2[SALT_INDEX], "different salt" ) if @@allPass puts "*** ALL TESTS PASS ***" else puts "*** FAILURES ***" end return @@allPass end |
.secure_hash(password) ⇒ Object
53 54 55 56 57 58 59 60 61 62 63 64 65 66 |
# File 'lib/reedb/security/secure_hash.rb', line 53 def self.secure_hash password salt = SecureRandom.base64(SALT_BYTE_SIZE) sha256 = OpenSSL::Digest::SHA256.new len = sha256.digest_length pbkdf2 = OpenSSL::PKCS5.pbkdf2_hmac( password, salt, PBKDF2_ITERATIONS, len, sha256 ) return [PBKDF2_ITERATIONS, salt, Base64.encode64( pbkdf2 )].join( SECTION_DELIMITER ) end |
.validate_pw(password, correctHash) ⇒ Object
Checks if a password is correct given a hash of the correct one. correctHash must be a hash string generated with createHash.
70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 |
# File 'lib/reedb/security/secure_hash.rb', line 70 def self.validate_pw(password, correctHash) params = correctHash.split(SECTION_DELIMITER) return false if params.length != HASH_SECTIONS salt = params[SALT_INDEX] hash = [HASH_INDEX] sha256 = OpenSSL::Digest::SHA256.new len = sha256.digest_length confirmed = Base64.decode64(params[HASH_INDEX]) test_hash = OpenSSL::PKCS5.pbkdf2_hmac( password, salt, PBKDF2_ITERATIONS, len, sha256 ) return confirmed == test_hash end |