node.js - Node 加密: en/decrypt token for validation

标签 node.js encryption cryptography token

我想要加密和解密 token ,以便能够在不访问数据库的情况下确定它是否可能是有效 token 。

我的代码适用于看起来“完全不同”的 token ,但如果我只更改一个字母,则会返回结果(不会引发错误),因此看起来 token 是有效的......!?

这是我的代码(加上手动更改字母):

var crypto = require("crypto");

var cryptSecret = "a!=ksljdk34ajSDkl";
var token = "1d3889647173d415e24195ce5cafc36c1edcc053";

function _encodeUrlSaveBase64(str) {
  return str.replace(/\+/g, "-").replace(/\//g, "_").replace(/\=+$/, "");
}

function _decodeUrlSaveBase64(str) {
  str = (str + "===").slice(0, str.length + (str.length % 4));
  return str.replace(/-/g, "+").replace(/_/g, "/");
}

function _encrypt(data) {
  var cipher = crypto.createCipher("aes256", cryptSecret);
  var str = cipher.update(data, "utf8", "base64") + cipher.final("base64");
  str = _encodeUrlSaveBase64(str);
  return str;
}

function _decrypt(data) {
  var str = _decodeUrlSaveBase64(data);
  var decipher = crypto.createDecipher("aes256", cryptSecret);
  str = decipher.update(str, "base64", "utf8") + decipher.final("utf8");
  return str;
}

console.log("token:    ", token);
var encrypted = _encrypt(token);
console.log("encrypted:", encrypted);
// change fourth letter to upper-case B (instead of lower-case)
encrypted = "bYzBYnU8FX7Rxs6Hae-yZkXvlwlRnhMQdLrT07e6YBy79nrK8FIpbKbxsYsXUmbk";
console.log("changed  :", encrypted);
console.log("decrypt  :", _decrypt(encrypted));

它输出:

token:     1d3889647173d415e24195ce5cafc36c1edcc053
encrypted: bYzbYnU8FX7Rxs6Hae-yZkXvlwlRnhMQdLrT07e6YBy79nrK8FIpbKbxsYsXUmbk
changed  : bYzBYnU8FX7Rxs6Hae-yZkXvlwlRnhMQdLrT07e6YBy79nrK8FIpbKbxsYsXUmbk
decrypt  : �g�
1��/b���e2.195ce5cafc36c1edcc053

通常应该在哪里抛出这样的错误:

TypeError: error:06065064:digital envelope routines:EVP_DecryptFinal_ex:bad decrypt
    at Decipher.Cipher.final (crypto.js:302:27)
    at _decrypt (/***/test.js:25:59)
    at Object.<anonymous> (/***/test.js:35:27)
    at Module._compile (module.js:449:26)
    at Object.Module._extensions..js (module.js:467:10)
    at Module.load (module.js:349:32)
    at Function.Module._load (module.js:305:12)
    at Function.Module.runMain (module.js:490:10)
    at startup (node.js:123:16)
    at node.js:1128:3

我做错了什么还是这就是它的工作方式?

最佳答案

您需要区分加密(隐藏某些内容)和签名(验证某些内容)。在您的情况下,您隐藏了 token 的内容。验证 token 的一个简单解决方案是使用 secret 的哈希:

hashvalue = tokenvalue + hashfunction(tokenvalue + secret)

验证时,将token值截取,重新计算hash值,如果不匹配,则一定是有人篡改了token。一个流行的例子是 LTPA v1 .

该方案有一些缺点,最大的缺点是各方都需要 secret 来验证 token ,因此能够创建新的有效 token 。因此,IBM 切换到 LTPA v2 的公钥。

关于node.js - Node 加密: en/decrypt token for validation,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/21765499/

相关文章:

javascript - EJS Javascript 中分解语句的规则是什么?

node.js - 从单独的第三方 Node 模块运行 Sequelize 迁移文件?

c# - 在哪里存储 Windows 服务的 X509 证书?

c# - 在 Angular 中加密并在 C# 上解密

node.js - 为什么 Grunt 会失败?

javascript - 用于测试的环回应用程序示例?

c# - 将加密代码从 Java 移植到 C# 时存在一些等价问题

encryption - 如何将 pgp 私钥传输到另一台计算机?

Java servlet : only allow own client

encryption - pkcs11 - 有关 `C_EncryptUpdate/C_EncryptFinal` 的问题