Skip to content

Instantly share code, notes, and snippets.

@kkosuge
Last active April 8, 2022 09:46
Show Gist options
  • Star 12 You must be signed in to star a gist
  • Fork 2 You must be signed in to fork a gist
  • Save kkosuge/4d09f014a8f8dc8aa365 to your computer and use it in GitHub Desktop.
Save kkosuge/4d09f014a8f8dc8aa365 to your computer and use it in GitHub Desktop.
PHP <=> Ruby ( OpenSSL AES-256-CBC )
<?php
const PASSWORD = '!!!!!sufficiently_long_password!!!!!';
const CIPHER_METHOD = 'AES-256-CBC';
function encrypt($str) {
$iv_length = openssl_cipher_iv_length(CIPHER_METHOD);
$iv = mcrypt_create_iv($iv_length, MCRYPT_RAND);
$str = $iv.$str;
$val = openssl_encrypt($str, CIPHER_METHOD, PASSWORD, 0, $iv);
return str_replace(array('+', '/', '='), array('_', '-', '.'), $val);
}
function decrypt($str) {
$val = str_replace(array('_','-', '.'), array('+', '/', '='), $str);
$data = base64_decode($val);
$iv_length = openssl_cipher_iv_length(CIPHER_METHOD);
$body_data = substr($data, $iv_length);
$iv = substr($data, 0, $iv_length);
$base64_body_data = base64_encode($body_data);
return openssl_decrypt($base64_body_data, CIPHER_METHOD, PASSWORD, 0, $iv);
}
$plain_data = 'secret text';
$encrypted = encrypt($plain_data);
$decrypted = decrypt($encrypted);
echo $encrypted."\n";
echo $decrypted."\n";
require 'openssl'
require 'base64'
require 'pry'
PASSWORD = '!!!!!sufficiently_long_password!!!!!';
CIPHER_METHOD = 'AES-256-CBC'
def encrypt(str)
cipher = OpenSSL::Cipher.new(CIPHER_METHOD)
cipher.encrypt
iv = OpenSSL::Random.random_bytes(cipher.iv_len)
cipher.iv = iv
cipher.key = PASSWORD
str = iv + str
data = cipher.update(str) + cipher.final
Base64.urlsafe_encode64(data)
end
def decrypt(str)
data = Base64.urlsafe_decode64(str)
cipher = OpenSSL::Cipher.new(CIPHER_METHOD)
cipher.decrypt
cipher.key = PASSWORD
cipher.iv = data[0..(cipher.iv_len-1)]
data_body = data[cipher.iv_len..-1]
cipher.update(data_body) + cipher.final
end
plain_data = 'secret text';
encrypted = encrypt(plain_data)
decrypted = decrypt(encrypted)
puts encrypted
puts decrypted
@MonteShaffer
Copy link

If the goal is to allow PHP to encode and RUBY to decode, and vice versa, it is important to note a few things.

The encrypt/decrypt functions in RUBY need to add the same str_replace functions usings gsub:

$val = str_replace(array('_','-', '.'), array('+', '/', '='), $str);

In addition, with the current setup, the variable PASSWORD must be 32 characters long or RUBY will complain.

@daniel-nelson
Copy link

You don't need to string replace, you just need to use strict_encode64 and strict_decode64 on the ruby side instead of the urlsafe variants.

@garlou
Copy link

garlou commented Apr 8, 2022

Thank you. Just a quick note. As off ruby 2.4 plain text password stopped being supported. Its required a 32 bytes password which I generated using key = SecureRandom.random_bytes(32).
To store it (on .env file i.e) I base64 encoded it using Base64.encode64(key), Then when decypting just decode it using cipher.key = Base64.decode64(key).
On PHP side is base64_decode($key);
And all works now 👍

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment