Есть несколько тонких вещей, которые делают это неудачей.Самый важный из них - вы не указываете IV в своем коде, поэтому для вас будет сгенерировано случайное значение.Вы могли бы заметить, что таким способом вы даже не можете расшифровать свой зашифрованный текст на одном и том же языке программирования.
Так что вам нужно предоставить явный IV для обеих реализаций.Но прежде чем я покажу вам код, несколько советов:
Генерация ключей :
Blowfish работает на 64-битных блоках, размер ключа варьируется, но OpenSSL (который в настоящее время работаетРеализация шифров как в Ruby, так и в node.js) по умолчанию использует 128 бит, то есть 16 байтов.
Таким образом, ваш ключ нарушает два принципа - первый: он просто слишком длинный.Это шестнадцатеричное представление хэша SHA-1, которое составляет 20 байтов * 2 = 40 байтов вместо 16. В большинстве случаев это нормально, потому что реализация соответствующим образом усекает значения, но это то, что вы не должны зависит от.
Вторая ошибка, гораздо более серьезная, заключается в том, что вы используете шестнадцатеричное представление вместо необработанных байтов: большая проблема безопасности!Шестнадцатеричные символы не являются случайными вообще, поэтому вы фактически уменьшаете энтропию вашего ввода до половины длины (потому что нижележащие байты были случайными).
Безопасный способ генерации случайных ключей - использование OpenSSL :: Random
key = OpenSSL::Random.random_bytes(cipher_key_len)
Третья ошибка заключается в том, чтобы сохранить ваш ключ жестко закодированным в источниках.Это плохая идея.Минимум, что вам нужно сделать, это сохранить его в другом месте в файловой системе, где доступ строго ограничен.Смотрите также мой ответ на другой вопрос.Ключ должен храниться вне диапазона и только динамически загружаться в приложение.
Шифр :
Blowfish стареет.Он по-прежнему считается непрерывным в том смысле, что грубое принуждение - единственный способ его сломать.Но пространство поиска 2 ^ 64 не доступно для находчивых злоумышленников.Поэтому вам действительно следует перейти к AES.
Padding :
Пэды OpenSSL с использованием PKCS5Padding (также известный как PKCS7Padding) по умолчанию.Ruby извлекает из этого выгоду, и моя ставка - это node.js, который тоже этим пользуется - поэтому вы должны быть в безопасности.
Теперь перейдем к рабочему решению.Нам нужно сгенерировать IV, Blowfish требует, чтобы он был 64-битным - 8 байтов.Вам понадобятся rbytes, чтобы получить безопасные случайные числа в узле.IV может быть жестко закодирован в ваших источниках (это общедоступная информация, не влияет на безопасность), но он должен быть одинаковым для обеих сторон.Вы должны предварительно сгенерировать значение и использовать его как для node.js, так и для Ruby.
/*node.js*/
var rbytes = require('rbytes');
var iv = rbytes.randomBytes(8);
/*see advice above - this should be out-of-band*/
var key = rbytes.randomBytes(16);
var encrypted = "";
var cipher = crypto.createCipheriv('bf-cbc', key, iv);
encrypted += cipher.update('text');
encrypted += cipher.final('hex');
Теперь часть Ruby:
require 'openssl'
c = OpenSSL::Cipher::Cipher.new("bf-cbc")
c.encrypt
# should be out-of-band again
c.key = OpenSSL::Random.random_bytes(16)
# may be public but has to be the same for Ruby and node
iv = OpenSSL::Random.random_bytes(8)
c.iv = iv
e = c.update("text")
e << c.final
puts e.unpack('H*')[0]