From 6965c0dd41fa386fd58e45475d6eef9d3005376f Mon Sep 17 00:00:00 2001 From: Guillaume Vincent Date: Fri, 18 Nov 2016 14:09:41 +0100 Subject: [PATCH] add render Password tests --- index.js | 1 + package.json | 1 + src/v2.js | 16 ++++++++++++++++ tests/v2/renderPassword.tests.js | 28 ++++++++++++++++++++++++++++ tests/v2/renderPassword.tests.py | 10 ++++++++++ 5 files changed, 56 insertions(+) create mode 100644 tests/v2/renderPassword.tests.js create mode 100644 tests/v2/renderPassword.tests.py diff --git a/index.js b/index.js index 0065932..2ef1268 100644 --- a/index.js +++ b/index.js @@ -16,6 +16,7 @@ module.exports = { _createHmac: _createHmac, _calcEntropy: v2.calcEntropy, _getSetOfCharacters: v2.getSetOfCharacters, + _renderPassword: v2.renderPassword, }; function _encryptLogin(login, masterPassword, options) { diff --git a/package.json b/package.json index 1cc8b70..5fec02c 100644 --- a/package.json +++ b/package.json @@ -23,6 +23,7 @@ "test:browser": "npm run build && karma start tests/karma.config.js" }, "dependencies": { + "big-integer": "^1.6.17", "bluebird": "^3.4.6", "create-hmac": "^1.1.4", "pbkdf2": "^3.0.9", diff --git a/src/v2.js b/src/v2.js index ca099d7..d283bfb 100644 --- a/src/v2.js +++ b/src/v2.js @@ -1,5 +1,6 @@ var Promise = require("bluebird"); var pbkdf2 = require('pbkdf2'); +var bigInt = require("big-integer"); exports.calcEntropy = function (site, login, masterPassword, passwordProfile) { return new Promise(function (resolve, reject) { @@ -36,4 +37,19 @@ exports.getSetOfCharacters = function (passwordProfile) { } }); return setOfCharacters; +}; + +function consumeEntropy(generatedPassword, quotient, setOfCharacters, maxLength) { + if (generatedPassword.length >= maxLength) { + return generatedPassword + } + var longDivision = quotient.divmod(setOfCharacters.length); + generatedPassword += setOfCharacters[longDivision.remainder]; + return consumeEntropy(generatedPassword, longDivision.quotient, setOfCharacters, maxLength) +} + +exports.renderPassword = function (entropy, setOfCharacters, passwordProfile) { + var _passwordProfile = passwordProfile !== undefined ? passwordProfile : {}; + var length = _passwordProfile.length || 14; + return consumeEntropy('', bigInt(entropy, 16), setOfCharacters, length); }; \ No newline at end of file diff --git a/tests/v2/renderPassword.tests.js b/tests/v2/renderPassword.tests.js new file mode 100644 index 0000000..cbcde8e --- /dev/null +++ b/tests/v2/renderPassword.tests.js @@ -0,0 +1,28 @@ +var assert = chai.assert; + +describe('LessPass', function () { + it('render password use remainder of long division beetween entropy and set of chars length as an index ', function () { + var entropy = 'dc33d431bce2b01182c613382483ccdb0e2f66482cbba5e9d07dab34acc7eb1e'; + var setOfCharacters = 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789'; + assert.equal('y', LessPass._renderPassword(entropy, setOfCharacters)[0]); + }); + it('render password use quotient as second entropy recursively', function () { + var entropy = 'dc33d431bce2b01182c613382483ccdb0e2f66482cbba5e9d07dab34acc7eb1e'; + var setOfCharacters = 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789'; + assert.equal('5', LessPass._renderPassword(entropy, setOfCharacters)[1]); + }); + it('render password has default length of 14', function () { + var entropy = 'dc33d431bce2b01182c613382483ccdb0e2f66482cbba5e9d07dab34acc7eb1e'; + var setOfCharacters = 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789'; + assert.equal(14, LessPass._renderPassword(entropy, setOfCharacters).length); + }); + it('render password can specify length', function () { + var entropy = 'dc33d431bce2b01182c613382483ccdb0e2f66482cbba5e9d07dab34acc7eb1e'; + var setOfCharacters = 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789'; + var passwordProfile = { + length: 20 + }; + assert.equal(20, LessPass._renderPassword(entropy, setOfCharacters, passwordProfile).length); + }); + +}); \ No newline at end of file diff --git a/tests/v2/renderPassword.tests.py b/tests/v2/renderPassword.tests.py new file mode 100644 index 0000000..a8f7708 --- /dev/null +++ b/tests/v2/renderPassword.tests.py @@ -0,0 +1,10 @@ +def renderPassword(mdp, quotient, alphabet): + if len(mdp) > 14: + return mdp + quotient, remainder = divmod(quotient, len(alphabet)) + mdp += alphabet[remainder] + return renderPassword(mdp, quotient, alphabet) + + +alphabet = 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789' +print(renderPassword('', int('dc33d431bce2b01182c613382483ccdb0e2f66482cbba5e9d07dab34acc7eb1e', 16), alphabet))