Sha256: 2f556020a31a1e3a4e7e8a6c2cac2d6afe56e47dae6ac76a704c8a3889d7e38e

Contents?: true

Size: 1.68 KB

Versions: 13

Compression:

Stored size: 1.68 KB

Contents

# frozen_string_literal: true

require 'openssl'

module Rack
  module Protection
    module Encryptor
      CIPHER     = 'aes-256-gcm'
      DELIMITER  = '--'

      def self.base64_encode(str)
        [str].pack('m0')
      end

      def self.base64_decode(str)
        str.unpack1('m0')
      end

      def self.encrypt_message(data, secret, auth_data = '')
        raise ArgumentError, 'data cannot be nil' if data.nil?

        cipher = OpenSSL::Cipher.new(CIPHER)
        cipher.encrypt
        cipher.key = secret[0, cipher.key_len]

        # Rely on OpenSSL for the initialization vector
        iv = cipher.random_iv

        # This must be set to properly use AES GCM for the OpenSSL module
        cipher.auth_data = auth_data

        cipher_text = cipher.update(data)
        cipher_text << cipher.final

        "#{base64_encode cipher_text}#{DELIMITER}#{base64_encode iv}#{DELIMITER}#{base64_encode cipher.auth_tag}"
      end

      def self.decrypt_message(data, secret)
        return unless data

        cipher = OpenSSL::Cipher.new(CIPHER)
        cipher_text, iv, auth_tag = data.split(DELIMITER, 3).map! { |v| base64_decode(v) }

        # This check is from ActiveSupport::MessageEncryptor
        # see: https://github.com/ruby/openssl/issues/63
        return if auth_tag.nil? || auth_tag.bytes.length != 16

        cipher.decrypt
        cipher.key = secret[0, cipher.key_len]
        cipher.iv  = iv
        cipher.auth_tag = auth_tag
        cipher.auth_data = ''

        decrypted_data = cipher.update(cipher_text)
        decrypted_data << cipher.final
        decrypted_data
      rescue OpenSSL::Cipher::CipherError, TypeError, ArgumentError
        nil
      end
    end
  end
end

Version data entries

13 entries across 13 versions & 2 rubygems

Version Path
rack-protection-3.2.0 lib/rack/protection/encryptor.rb
rack-protection-3.1.0 lib/rack/protection/encryptor.rb
rubypitaya-3.12.5 ./lib/rubypitaya/app-template/vendor/bundle/ruby/3.1.0/gems/rack-protection-3.0.5/lib/rack/protection/encryptor.rb
rack-protection-3.0.6 lib/rack/protection/encryptor.rb
rubypitaya-3.12.4 ./lib/rubypitaya/app-template/vendor/bundle/ruby/3.1.0/gems/rack-protection-3.0.5/lib/rack/protection/encryptor.rb
rubypitaya-3.12.3 ./lib/rubypitaya/app-template/vendor/bundle/ruby/3.1.0/gems/rack-protection-3.0.5/lib/rack/protection/encryptor.rb
rubypitaya-3.12.2 ./lib/rubypitaya/app-template/vendor/bundle/ruby/3.1.0/gems/rack-protection-3.0.5/lib/rack/protection/encryptor.rb
rack-protection-3.0.5 lib/rack/protection/encryptor.rb
rack-protection-3.0.4 lib/rack/protection/encryptor.rb
rack-protection-3.0.3 lib/rack/protection/encryptor.rb
rack-protection-3.0.2 lib/rack/protection/encryptor.rb
rack-protection-3.0.1 lib/rack/protection/encryptor.rb
rack-protection-3.0.0 lib/rack/protection/encryptor.rb