Это ожидаемое поведение в соответствии со схемами заполнения для подписи и шифрования RSA, реализованными OpenSSL, , которые crypto
используют .
Я не уверен, для чего вы хотите использовать функции privateEncrypt()
и publicDecrypt()
. Если вы намереваетесь подписать данные, см. Мое обновление ниже. В любом случае, для этих функций документация crypto
объясняет, что она только раскрывает RSA_PKCS1_PADDING
, который OpenSSL отображает на детерминированную схему заполнения RSASSA-PKCS1-v1_5 под капотом. Это означает, что для одного и того же ключа и одних и тех же данных результирующие данные будут одинаковыми.
Для шифрования и дешифрования, с помощью publicEncrypt()
и privateDecrypt()
, вы выбрали режим RSA_PKCS1_PADDING
. Это преобразуется в RSAES-PKCS1-v1_5, схему, которая включает в себя случайные элементы, которые вызывают различные выходные данные, которые вы наблюдаете в ваших повторных прогонах. Согласно документации, crypto
использует заполнение RSA_PKCS1_OAEP_PADDING
по умолчанию. Это означает Оптимальное асимметричное заполнение шифрования , которое также является недетерминированным.
Сводка схем, определенных PKCS # 1, приведена в Схемы PKCS # 1 .
Обновление: вы можете использовать Sign class
вместо функций privateEncrypt()
и publicDecrypt()
. Его функция sign
() поддерживает вероятностный режим заполнения, который OpenSSL поддерживает через RSASSA-PSS. Используя ваш пример кода в качестве отправной точки, он будет выглядеть примерно так:
const sign = crypto.createSign('SHA256')
sign.update(Buffer.from(originMSG, 'utf8'))
signature = sign.sign({key:PRIVKEY, padding:crypto.constants.RSA_PKCS1_PSS_PADDING}).toString('base64')
Подпись будет отличаться каждый раз. Обратите внимание, что вы не можете «расшифровать» его, это односторонняя операция. Вы можете проверить это только с помощью открытого ключа с классом Verify
:
const verify = crypto.createVerify('SHA256')
verify.update(Buffer.from(originMSG, 'utf8'))
verifyRes = verify.verify({key:PUBKEY, padding:crypto.constants.RSA_PKCS1_PSS_PADDING}, Buffer.from(signature, 'base64'))