Hendrik
Hendrik

Reputation: 4939

Laravel Crypt::decrypt migration to ruby

for a customer we are migrating a Laravel application to a Ruby application. We have some data stored in the database that we would like to decrypt in the ruby world.

This is the laravel part that was used to encrypt the data: https://laravel.com/docs/5.0/encryption

Now when importing the data to ruby we need a counter part that can decrypt the data.

In the laravel console I was able to decrypt the data like this:

>>> Crypt::decrypt('eyJpdiI6ImZyek9ZTjJNSW5ZYlhSa2ZYUldVbEE9PSIsInZhbHVlIjoia20zMTRLWEpCdXM2K05DZDBHSlE5SDlcL2pYVXk5aE5RWWR3dHFQT1dGQzA9IiwibWFjIjoiZWZlNGE3NTRhMDDlNzk2MjhlYjI1Mzc1NGNiYmRjNDMwZjM1NzdiMzkyZTU4ZjA4ZDNkMGE0YjUyOTBjMDAzOCJA')
=> "123123123123"

I am no laravel expert, but in the app.php file a secret key was set. So I need to be able to pass it somehow to the decrypt function.

The goal is to have a ruby function that takes the laravel password, encryption key and returns the decrypted value.

def decrypt_laravel_crypt(value, encryption_key)
end

Thanks for the help!

Upvotes: 0

Views: 303

Answers (1)

Mike Mollick
Mike Mollick

Reputation: 61

You can reverse engineer Laravel's Encrypter::decrypt method using mostly standard libs. Laravel will serialize data before encrypting it unless told explicitly not to. This means attempting to unserialize the decrypted string prior to using it.

require 'base64'
require 'openssl'
require 'json'
require 'php_serialize'

def lara_decrypt(encryptedString, appKey)
   data = JSON.parse(Base64::decode64(encryptedString))

   decipher = OpenSSL::Cipher.new('aes-256-cbc')
   decipher.decrypt
   decipher.key = Base64::decode64(appKey)
   decipher.iv = Base64::decode64(data['iv'])
   decrypted = decipher.update(Base64::decode64(data['value'])) + decipher.final
   begin
      PHP.unserialize(decrypted)
   rescue
      decrypted
   end
end

Also when you set the app key be sure to drop base64: from the beginning of it (if it's there).

Upvotes: 2

Related Questions