шифрование с использованием ase256 дает различный вывод в python и nodejs - PullRequest
1 голос
/ 18 марта 2019

Я пытаюсь зашифровать строку «1», используя ключ = «secret_key» и текст «11869021012».Ранее я написал это в nodejs.Теперь я хочу перенести это на Python.но здесь удивительно, что оба дают разные выходные данные.

var crypto = require('crypto');

function getBytes (str) {
  let bytes = [], char;
  str = encodeURI(str);
  while (str.length) {
    char = str.slice(0, 1);
    str = str.slice(1);

    if ('%' !== char) {
      bytes.push(char.charCodeAt(0));
    } else {
      char = str.slice(0, 2);
      str = str.slice(2);

      bytes.push(parseInt(char, 16));
    }
  }
  return bytes;
};


function getIV (str, bytes){
    iv = getBytes(str);
    if(!bytes) bytes = 16;
    for(let i=iv.length;i<bytes;i++) {
      iv.push(0);
    }
    return Buffer.from(iv);
};

function getKey (pwd){
    pwd = Buffer.from(getBytes(pwd), 'utf-8');
    let hash = crypto.createHash('sha256');
    pwd = hash.update(pwd).digest();
    return pwd;
};

function createCipherIV (algorithm, input_key, iv_input, text){
    let iv = getIV(iv_input);
    let key = getKey(input_key);
    let cipher = crypto.createCipheriv(algorithm, key, iv);
    let encrypted = cipher.update(text)
    encrypted += cipher.final('base64');
    return encrypted;
}

output = createCipherIV('aes256', 'secret_key', '11869021012', '1') 
console.log(output)

Это производит вывод: s6LMaE/YRT6y8vr2SehLKw==

код Python:

# AES 256 encryption/decryption using pycrypto library
import base64
import hashlib

from Crypto.Cipher import AES
from Crypto import Random

BLOCK_SIZE = 16
pad = lambda s: s + (BLOCK_SIZE - len(s) % BLOCK_SIZE) * chr(BLOCK_SIZE - len(s) % BLOCK_SIZE)
unpad = lambda s: s[:-ord(s[len(s) - 1:])]

password = "secret_key"

def encrypt(raw, password):
    private_key = hashlib.sha256(bytearray(password, "utf-8")).digest()
    raw = pad(raw)
    iv = b'11869021012\x00\x00\x00\x00\x00'
    cleartext = bytearray(raw, 'utf-8')
    cipher = AES.new(private_key, AES.MODE_CBC, iv)

    return base64.b64encode(iv + cipher.encrypt(cleartext))

# First let us encrypt secret message
encrypted = encrypt("1", password)
print(encrypted)

Это производит вывод: MTE4NjkwMjEwMTIAAAAAALOizGhP2EU+svL69knoSys=

Я использовал алгоритм aes256 здесь для шифрования сообщения.Ясно, что они очень близки, но узел, кажется, дополняет вывод дополнительными байтами.Любые идеи, как я могу заставить эти два взаимодействовать?

1 Ответ

1 голос
/ 18 марта 2019

Во-первых, в безопасной криптосистеме вы должны ожидать, что выходные данные будут отличаться при каждом шифровании, даже с использованием одного и того же кода.Тот факт, что ваш не означает, что это небезопасный шифр.Как правило, это делается путем добавления случайного IV.

Ваш IV - «11869021012», что ужасно (потому что это не случайно, и даже не 16 байтов), но кажется, что вы используете то же самоев обоих случаях, так что все в порядке.

Ваш пароль - SHA-256 строки, что является ужасным способом создания ключа, но, тем не менее, вы, похоже, делаете это одинаково в обоих случаяхтак что все в порядке.

Ваша проблема в том, что код Python выдает IV, за которым следует текст шифра.Ваш код JS не испускает IV;он только излучает зашифрованный текст.Таким образом, вы, вероятно, имели в виду это в Python:

return base64.b64encode(cipher.encrypt(cleartext))

Или вам нужно переделать JavaScript, чтобы склеить IV и текст шифра перед кодировкой Base64.

...