我有一个PHP代码,用AES-128加密一个ip地址:
$ip = "MY_IP";
$secret = "MY_KEY";
$ip = @mcrypt_ecb(MCRYPT_RIJNDAEL_128, $secret, $ip, MCRYPT_ENCRYPT);
$encrypted = bin2hex($ip); // encrypted: 2854edb405cb7230ba1f4b87acddba8a
我需要做的是使用相同的代码但使用javascript / node.js。我在crypto node.js本机模块中搜索过,但是我无法重现相同的结果:
var crypto = require('crypto');
var ip = "MY_IP";
var secret = "MY_KEY";
var cipher = crypto.createCipher("AES-128-ECB", secret);
var encrypted = cipher.update(ip, 'utf8', 'hex');
encrypted += cipher.final('hex'); // encrypted: e84c06888696edda0139e98fc2c0a8cc
有人有想法吗?
答案 0 :(得分:3)
我发布得太快,找到了解决方案:
$> npm install mcrypt
然后是代码:
var MCrypt = require('mcrypt').MCrypt;
var ip = "MY_IP";
var secret = "MY_KEY"
var desEcb = new MCrypt('rijndael-128', 'ecb');
desEcb.open(secret);
var cipherText = desEcb.encrypt(ip); // cipherText: 2854edb405cb7230ba1f4b87acddba8a
MCrypt github获取更多加密工具:https://github.com/tugrul/node-mcrypt
答案 1 :(得分:3)
这里的问题是PHP的mcrypt扩展(和节点的createCipher()
)在幕后做了一些你可能不知道的事情。
首先,createCipher()
接受使用MD5进行哈希处理的“密码”,以获取实际键。所以你应该使用的是createCipheriv()
,它允许你直接传递密钥(和IV),就像PHP的mcrypt接受的那样。在ECB模式下,IV被忽略,因此您只需为IV参数传入一个空字符串。
其次,如果PHP密码小于密码的块大小和密钥大小,那么PHP的mcrypt会错误地将输入和你的密钥用空字节填充。
因此,对于AES-128-ECB,我们需要确保输入和密钥长度是16个字节的倍数。通过所有这些知识,我们发现内置crypto
模块的适当代码可能类似于:
var crypto = require('crypto');
function makePadded(str) {
var buf;
var len = str.length;
if (str.length % 16)
len = str.length + (16 - str.length % 16);
buf = new Buffer(len);
buf.fill(0);
buf.write(str, 0, str.length);
return buf;
}
var ip = makePadded('MY_IP');
var secret = makePadded('MY_KEY');
var cipher = crypto.createCipheriv("AES-128-ECB", secret, '');
var encrypted = cipher.update(ip, 'binary', 'hex');
encrypted += cipher.final('hex');
// Slice off at 16 bytes to match the input length
encrypted = encrypted.slice(0, 32);
console.log(encrypted);
值得一提的最后一件事是,PHP中的MCRYPT_RIJNDAEL_128
可用于执行128,192或256位加密。因此,在PHP 0 < keylen <= 16
中,将使用128位加密,如果16 < keylen <= 24
将使用24 < keylen <= 32
,将使用192位加密,angular.module("demoApp", ['ngRoute'])
.config(['$routeProvider', '$locationProvider',
function ($routeProvider, $locationProvider) {
$routeProvider.
when('someURL', {
templateUrl: 'someTemplate.html',
controller: 'CreateGrids'
});
$locationProvider.html5Mode(true);
}
])
.factory("servers", function () {
var servers = {};
...
return servers;
})
.factory("setup", function () {
var setup = {};
...
return setup;
})
.factory("gridservice", ['$http', function ($http) {
var gridservice = {};
...
return gridservice;
}])
.controller('MainCtrl', ['$route', '$routeParams', '$location',
function ($route, $routeParams, $location) {
this.$route = $route;
this.$location = $location;
this.$routeParams = $routeParams;
console.log(this.$routeParams);
}
])
.controller("CreateGrids", ['$routeParams', '$scope', '$http', 'setup', 'server', 'gridservice', function ($routeParams, $scope, $http, setup, servers, gridservice) {
this.name = 'CreateGrids';
this.params = $routeParams;
console.log($routeParams);
...
}])
.controller("ServerRepeat", ['$scope', 'servers', 'setup', function ($scope, servers, setup) {
...
}
}]);
将使用256位加密。但是在节点中,您需要适当地调整密码名称,因为节点不会执行PHP所做的那种“自动调整”。
答案 2 :(得分:0)
- 密码必须是'二进制'编码的字符串或缓冲区。在PHP中,不推荐使用的@mcrypt_ecb期望一个键是一个字符串