javascript - 如何让 window.crypto.subtle 输出与 'crypto' js 库相同的签名?

标签 javascript encryption browser cryptography signature

我想使用内置的浏览器加密对象,而不是在浏览器项目中导入加密库。

我不想需要这个。

npm i crypto

以下代码说明了尝试使用这两个库对简单消息进行签名,但是在使用内置加密对象时我得到了不同的结果。输出被记录到控制台。

// START CRYPTO LIBRARY METHOD
import crypto from 'crypto';

const HMAC_SHA256_KEY = {
    API_KEY: '***',
    SECRET_KEY: '***'
};

const queryString = `timestamp=${(new Date().getTime())}`;

const signature = crypto
    .createHmac('sha256', HMAC_SHA256_KEY.SECRET_KEY)
    .update(queryString)
    .digest('hex')

console.log("standard encrypt", signature);

// START NATIVE LIBRARY METHOD    
const getUtf8Bytes = (str: string) => {
    return new Uint8Array(
        [...(unescape(encodeURIComponent(str)))].map(c => c.charCodeAt(0))
    );
};

// @ts-ignore
const builtInCrypto = window.crypto || window.msCrypto;
builtInCrypto.subtle.importKey(
    'raw',
    getUtf8Bytes(HMAC_SHA256_KEY.SECRET_KEY),
    {
        name: 'HMAC', hash: 'SHA-256'
    },
    true, ['sign']
).then(key => {
    builtInCrypto.subtle.sign(
        'HMAC',
        key,
        getUtf8Bytes(queryString))
        .then(signature => {
            console.log('builtIn Signature', btoa(String.fromCharCode(...(new Uint8Array(signature)))));
        })
})

显然我做错了什么,但是什么?为什么我会得到不同的 native 加密输出?

最佳答案

对于 HMAC_SHA256_KEY.SECRET_KEYqueryString相同值(最后一个参数取决于时间,因此每次运行都有不同的值) )两个脚本都返回相同 HMac,但采用不同编码,从而导致不同的输出。在 NodeJS/crypto 代码中,HMac 采用十六进制编码,在 JavaScript/Web Crypto API 代码中采用 Base64 编码。

为了确保输出相同,两个脚本中必须使用相同的编码。 JavaScript/Web Crypto API 代码中的 HMac 也必须是十六进制编码,请参见例如here对于合适的方法,或者 NodeJS/crypto 代码中的 HMac 必须采用 Base64 编码(通过传递 'base64' 而不是 'hex'作为digest的参数)。

关于javascript - 如何让 window.crypto.subtle 输出与 'crypto' js 库相同的签名?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/62988947/

相关文章:

javascript - 当滚动到达该 div 时更改内部 div 的 CSS

grails OpenPGP 解密不起作用

Java:从加密文件解密时出现错误填充错误

css - IE8/9 - CSS 文件的最大字节数

browser - 是否可以在 Web 应用程序中使用功能键(F2、F3...F11)?

javascript - 如何使用 JavaScript 将呈现的网页另存为图像?

当开发者工具关闭时,Javascript 在 IE 中失败

javascript - 在浏览器中读取 NFC 标签

javascript - 使用javascript随机图像并根据随机图像将背景颜色应用于页面

java - RSA加密Javascript和解密Java