前端加密的内容如何解密

问题描述 投票:0回答:1

这可能是一个小问题,但我既没有收到任何特定的错误,也没有得到任何解决方案。 我正在构建一个全栈项目。在这里,我需要一个条件,即我必须对项目后端部分的内容进行加密。我正在使用对称密钥加密并在 crypto-js 中使用

aes_256_gcm
。这是后端部分的代码。

import { randomBytes, createCipheriv } from "crypto";

const encryptMessage = (message, credential) => {
  const key = Buffer.from(credential, "utf-8");
  const iv = randomBytes(16);
  const cipher = createCipheriv("aes-256-gcm", key, iv);
  const encryptedMessage = Buffer.concat([
    cipher.update(message, "utf-8"),
    cipher.final(),
  ]);
  const tag = cipher.getAuthTag();

  return {
    iv: iv.toString("hex"),
    encryptedMessage: encryptedMessage.toString("hex"),
    tag: tag.toString("hex"),
  };
};


export default encryptMessage;

现在我将此内容存储在后端的变量中,然后将其传递到前端。

现在我尝试在前端使用代码中相同的

iv
tag
credential
来解密此消息。这是前端解密的代码。

const decryptMessage = async (encryptedData, credential) => {
  
  const decoder = new TextDecoder();
  
  const iv = new Uint8Array(encryptedData.iv.match(/.{1,2}/g).map((byte) => parseInt(byte, 16)));
  const encryptedMessage = new Uint8Array(encryptedData.encryptedMessage.match(/.{1,2}/g).map((byte) => parseInt(byte, 16)));
  const tag = new Uint8Array(encryptedData.tag.match(/.{1,2}/g).map((byte) => parseInt(byte, 16)));

  const encodedCredential =new TextEncoder().encode(credential)

  try{
  const key = await crypto.subtle.importKey(
    "raw",
    encodedCredential,
    { name: "AES-GCM" },
    false,
    ["decrypt"]
  );

  const decrypted = await crypto.subtle.decrypt(
    { name: "AES-GCM", 
    iv: iv,
    tag: tag },
    key,
    encryptedMessage
  );

    const decryptedMessage = decoder.decode(decrypted);

    console.log("Decrypted Message:", decryptedMessage);
    return decryptedMessage;

  }catch(error){
    console.error("Decryption Error:", error);
    throw new Error ("Decryption Failed" + error.message);
  }
}

export default decryptMessage

在这里我没有收到任何具体错误。刚刚得到

Decryption Error: Error
。当我应用
console.log()
时,我会在
decrypted
函数之前得到输出。 这就是我在另一个文件中调用此函数的方式。
const privateKey = await decryptMessage(keys, credential);

任何人都可以解释为什么会发生错误。如果它永远行不通,那怎么能做到这一点呢?意思是在后端加密内容并在前端解密。

reactjs node.js cryptojs aes-gcm webcrypto-api
1个回答
0
投票

crypto.subtle.decrypt()
的第一个参数中传递给
algorithm
的值不正确:
{ name: "AES-GCM", iv: iv, tag: tag }

根本没有为
tag
 定义属性 
AesGcmParams
。相反,在 GCM 的情况下,
crypto.subtle.decrypt()
期望将密文和标记的串联传递给第三个参数中的
data

固定代码(输入数据是使用 NodeJS 代码生成的):

(async () => {

const decryptMessage = async (encryptedData, credential) => {
  
  const decoder = new TextDecoder();
  
  const iv = new Uint8Array(encryptedData.iv.match(/.{1,2}/g).map((byte) => parseInt(byte, 16)));
  const encryptedMessage = new Uint8Array(encryptedData.encryptedMessage.match(/.{1,2}/g).map((byte) => parseInt(byte, 16)));
  const tag = new Uint8Array(encryptedData.tag.match(/.{1,2}/g).map((byte) => parseInt(byte, 16)));

  const encodedCredential =new TextEncoder().encode(credential)

  try{
    const key = await crypto.subtle.importKey(
      "raw",
      encodedCredential,
      { name: "AES-GCM" },
      false,
      ["decrypt"]
    );

    /*
    const decrypted = await crypto.subtle.decrypt(
      { name: "AES-GCM", 
      iv: iv,
      tag: tag },
      key,
      encryptedMessage
    );
    */
    const decrypted = await crypto.subtle.decrypt(
      { name: "AES-GCM", 
      iv: iv },
      key,
      new Uint8Array([...encryptedMessage, ...tag])
    );

    const decryptedMessage = decoder.decode(decrypted);

    console.log("Decrypted Message:", decryptedMessage);
    return decryptedMessage;

  } catch(error){
    console.error("Decryption Error:", error);
    throw new Error ("Decryption Failed" + error.message);
  }
}

var encryptedData = {
  iv: 'd38d7f07a4511b9f3cc79acb66b42528',
  encryptedMessage: 'd3da8f3da785b05ad4c2d462672379c287ba7640b971a3360d783e35acd6c9d1580555a1cb2927f1678147',
  tag: '7146b3fd125b59e718c4cd8cb39f8142'
};
var credential = '01234567890123456789012345678901';
var ct = '123ce86e38eed47a1658d8df832ed59eac3ac5465f0865583c2e48dba32b170307fa12d18e9f46691acd2c';
var dt = await decryptMessage(encryptedData, credential);

})();

© www.soinside.com 2019 - 2024. All rights reserved.