UNPKG

contingent

Version:

Create cryptographically-strong random numbers in node.js or the browser

89 lines (88 loc) 2.68 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); const utils_1 = require("./utils"); function randomBytes(crypto, n) { return crypto.randomBytes(n); } function randomBit(crypto) { return crypto.randomBit(); } function randomByte(crypto) { return crypto.randomByte(); } function randomInt(crypto) { return crypto.randomInt(); } function randomUInt(crypto) { return crypto.randomUint(); } function randomFloat(crypto) { return crypto.randomUint() / Math.pow(2, 32); } function randomIn(crypto, min, max) { if (max < min) { throw new Error('max should be >= min'); } return min + Math.floor((max - min) * randomFloat(crypto)); } function randomOf(crypto, list) { return list[randomIn(crypto, 0, list.length)]; } function roll(crypto, n) { if (n <= 0) { throw new Error('<roll> sides should be >= 1'); } return randomIn(crypto, 1, n + 1); } function shuffle(crypto, list) { for (let i = 0; i < list.length; i++) { const elem = randomIn(crypto, i, list.length); utils_1.swap(list, i, elem); } return list; } function pick(crypto, n, list) { if (n < 0 || n > list.length) { throw new Error(`num should be in the range [0, ${list.length}]`); } const copy = shuffle(crypto, list.slice()); return copy.slice(-n); } function select(crypto, n, list) { if (n < 0 || n > list.length) { throw new Error(`num should be in the range [0, ${list.length}]`); } const indexes = []; const len = list.length; for (let i = 0; i < n; i++) { indexes.push(randomIn(crypto, 0, len)); } return indexes.map(i => list[i]); } function replace(crypto, list, value) { const elem = randomIn(crypto, 0, list.length); list[elem] = value; return list; } function generate(len, create) { return new Array(len).fill(0).map(() => create()); } function core(crypto) { return { randomBytes: (n) => randomBytes(crypto, n), randomBit: () => randomBit(crypto), randomByte: () => randomByte(crypto), randomInt: () => randomInt(crypto), randomUInt: () => randomUInt(crypto), randomFloat: () => randomFloat(crypto), randomIn: (min, max) => randomIn(crypto, min, max), randomOf: (list) => randomOf(crypto, list), roll: (n) => roll(crypto, n), shuffle: (list) => shuffle(crypto, list), pick: (n, list) => pick(crypto, n, list), select: (n, list) => select(crypto, n, list), replace: (list, value) => replace(crypto, list, value), generate: (len, create) => generate(len, create), }; } exports.core = core;