Слияние кода завершено, страница обновится автоматически
const CryptoJS = require('./crypto-js-sha1.js')
// 需要CryptoJS
var HOTP = function(secret, window, counter) {
this.secret = secret || "123456";
this.window = window || 3;
this.counter = counter || 0;
};
HOTP.prototype.gen = function(counter) {
if (counter === null) {
if (this.counter === null) {
this.counter = 0;
}
counter = this.counter;
var ret = this.gen(counter);
this.counter += 1;
return ret;
}
var num = this.otp_gen_number(counter, this.secret);
num = num % 1000000;
if (num >= 100000) {
return String(num);
}
num = "000000" + num;
return num.substring(num.length - 6);
}
HOTP.prototype.verify = function(token, counter) {
if (counter === undefined) {
if (this.counter === undefined) {
this.counter = 0;
}
counter = this.counter;
return this.verify(token, counter);
}
for (var i = 0; i < this.window; i++) {
{
var tcounter = counter - i;
if (token === this.gen(tcounter))
return i;
}
if (i === 0)
continue;
{
var tcounter = counter + i;
if (token === this.gen(tcounter))
return i;
}
}
return null;
}
// 需要使用CryptoJS的HmacSHA1、WordArray,counter是32bit数字
HOTP.prototype.otp_gen_number = function(counter, secret) {
function convert(wordArray) {
var bytes20 = [];
for (var i = 0, j = 0; i < 5; i++) {
var v = wordArray.words[i];
bytes20[j++] = ((v >> 24) & 0xFF);
bytes20[j++] = ((v >> 16) & 0xFF);
bytes20[j++] = ((v >> 8) & 0xFF);
bytes20[j++] = ((v >> 0) & 0xFF);
}
var offset = bytes20[19] & 0xf;
var v = (bytes20[offset] & 0x7F) << 24 |
(bytes20[offset + 1] & 0xFF) << 16 |
(bytes20[offset + 2] & 0xFF) << 8 |
(bytes20[offset + 3] & 0xFF);
return v;
}
function _gen_number(counter, secret) {
var low = counter & 0xffffffff;
var high = Math.floor(counter / 4294967296); // 没有long类型,使用除以2^32代替右移32位
// console.log(counter, low, high);
var message = CryptoJS.lib.WordArray.create([high, low], 8);
var wordArray = CryptoJS.HmacSHA1(message, secret);
var num = convert(wordArray);
return num;
}
return _gen_number(counter, secret);
}
// ==================================================================================
var TOTP = function(secret, window, interval) {
this.hotp = new HOTP(secret, window, 0);
this.interval = interval || 30;
}
TOTP.prototype.gen = function(timestamp) {
timestamp = timestamp || new Date().getTime();
var timestamp_second = Math.floor(timestamp / 1000);
var tcounter = Math.floor(timestamp_second / this.interval);
return this.hotp.gen(tcounter);
}
TOTP.prototype.gen2 = function(timestamp) {
timestamp = timestamp || new Date().getTime();
var timestamp_second = Math.floor(timestamp / 1000);
var tcounter = Math.floor(timestamp_second / this.interval);
var token = this.hotp.gen(tcounter);
var step = timestamp_second % this.interval;
var refresh_time = tcounter * this.interval;
return {
token: token, // 生成的令牌
loop_length: this.interval, // 循环角度,循环长度
loop_step: step, // 循环角度,循环到的步骤
refresh_interval: this.interval * 1000, // 刷新周期
refresh_time: refresh_time * 1000, // 刷新时间
timestamp: timestamp, // 当前时间
};
}
TOTP.prototype.verify = function(token) {
var now = Math.floor(new Date().getTime() / 1000);
var tcounter = Math.floor(now / this.interval);
return this.hotp.verify(token, tcounter);
}
module.exports = {
HOTP: HOTP,
TOTP: TOTP,
}
Вы можете оставить комментарий после Вход в систему
Неприемлемый контент может быть отображен здесь и не будет показан на странице. Вы можете проверить и изменить его с помощью соответствующей функции редактирования.
Если вы подтверждаете, что содержание не содержит непристойной лексики/перенаправления на рекламу/насилия/вульгарной порнографии/нарушений/пиратства/ложного/незначительного или незаконного контента, связанного с национальными законами и предписаниями, вы можете нажать «Отправить» для подачи апелляции, и мы обработаем ее как можно скорее.
Опубликовать ( 0 )