class EncryptAttr::Encryptor

Constants

CIPHER

Attributes

secret_token[R]

Set the encryptor's secret token.

Public Class Methods

decrypt(secret_token, value) click to toggle source
# File lib/encrypt_attr/encryptor.rb, line 19
def self.decrypt(secret_token, value)
  new(secret_token).decrypt(value)
end
encrypt(secret_token, value) click to toggle source
# File lib/encrypt_attr/encryptor.rb, line 15
def self.encrypt(secret_token, value)
  new(secret_token).encrypt(value)
end
new(secret_token) click to toggle source
# File lib/encrypt_attr/encryptor.rb, line 26
def initialize(secret_token)
  @secret_token = secret_token
end
validate_secret_token(secret_token) click to toggle source
# File lib/encrypt_attr/encryptor.rb, line 5
def self.validate_secret_token(secret_token)
  return unless secret_token.size < 100

  offending_line = caller
                    .reject {|entry| entry.include?(__dir__) || entry.include?("forwardable.rb") }
                    .first[/^(.*?:\d+)/, 1]

  warn "[encrypt_attribute] secret token must have at least 100 characters (called from #{offending_line})"
end

Public Instance Methods

decode(value) click to toggle source
# File lib/encrypt_attr/encryptor.rb, line 65
def decode(value)
  Base64.decode64(value)
end
decrypt(value) click to toggle source
# File lib/encrypt_attr/encryptor.rb, line 41
def decrypt(value)
  cipher = OpenSSL::Cipher.new(CIPHER).decrypt
  key = Digest::SHA256.digest(secret_token)

  parts = value.split(";")

  if parts.size == 1
    value = decode(value)
    iv = key[0...cipher.iv_len]
  else
    iv = parts.first
    value = decode(parts.last)
  end

  cipher.key = key
  cipher.iv = iv

  cipher.update(value) + cipher.final
end
encode(value) click to toggle source
# File lib/encrypt_attr/encryptor.rb, line 61
def encode(value)
  Base64.encode64(value).chomp
end
encrypt(value) click to toggle source
# File lib/encrypt_attr/encryptor.rb, line 30
def encrypt(value)
  cipher = OpenSSL::Cipher.new(CIPHER).encrypt
  key = Digest::SHA256.digest(secret_token)
  iv = SecureRandom.random_bytes(cipher.iv_len).unpack("H*").first[0...cipher.iv_len]

  cipher.key = key
  cipher.iv = iv

  iv + ";" + encode(cipher.update(value) + cipher.final)
end