UNPKG

keyvenant

Version:

Keyvenant is a JavaScript tool to generate and export CovenantSQL keys to facilitate key management locally and in web extensions.

153 lines 9.88 kB
"use strict"; var __importDefault = (this && this.__importDefault) || function (mod) { return (mod && mod.__esModule) ? mod : { "default": mod }; }; var __importStar = (this && this.__importStar) || function (mod) { if (mod && mod.__esModule) return mod; var result = {}; if (mod != null) for (var k in mod) if (Object.hasOwnProperty.call(mod, k)) result[k] = mod[k]; result["default"] = mod; return result; }; Object.defineProperty(exports, "__esModule", { value: true }); const coinstring_1 = __importDefault(require("coinstring")); const utils_1 = require("./utils"); const THash_1 = __importDefault(require("./utils/THash")); const keygen = __importStar(require("./keygen")); const secretkey = __importStar(require("./secretkey")); const symmetric = __importStar(require("./symmetric")); /** * create CovenantSQL keystore * @param password master password user typed-in * @param salt kdf salt * @param addrVersion address version * @param privateKeyVersion private key encode version * @return keystore object */ function createKeystore(password, salt, addrVersion, privateKeyVersion) { // generate new key pair let prvKey = keygen.createPrivateKey(); let pubKey = keygen.privateKeyToPublicKey(prvKey); console.log('Print out private key for test', prvKey); // covert to address let address = keygen.publicKeyToAddress(pubKey, addrVersion); // get derived key from password let secretKey = secretkey.derive(password, salt); // prepare iv for symmetric encryption let iv = symmetric.generateIv(); let ciphertext = symmetric.encrypt(prvKey, secretKey, iv); let mac = constructMac(secretKey, ciphertext); let keystore = marshal(address, salt, mac, ciphertext, iv, privateKeyVersion); return keystore; } exports.createKeystore = createKeystore; /** * recover private key from keystore and password * @param password * @param keystore * @return private key string in hex */ function recoverFromKeystore(password, salt, keystore) { // get derived key from password let secretKey = secretkey.derive(password, salt); // prepare iv for symmetric encryption let iv = keystore.crypto.iv; let ciphertext = keystore.crypto.ciphertext; // check mac let macToVerify = constructMac(secretKey, ciphertext); if (macToVerify !== keystore.mac) { throw new Error('Input password is not valid for the keystore or version not compatible'); } // decrypt private key let prvKey = symmetric.decrypt(ciphertext, secretKey, iv); return prvKey; } exports.recoverFromKeystore = recoverFromKeystore; /** * construct keystore json * @param address wallet address * @param salt kdf salt * @param mac mac value * @param ciphertext encrypted text * @param iv symmetric iv * @param privateKeyVersion version hex * @return keystore object */ function marshal(address, salt, mac, ciphertext, iv, privateKeyVersion) { let encrypted = constructEncrypted(privateKeyVersion, iv, ciphertext); let keystore = { address, encrypted, mac, crypto: { cipher: 'aes-256', ciphertext, iv }, derivation: { kdf: 'sha256x2', salt }, version: privateKeyVersion, }; return keystore; } /** * construct Mac for password pre-check * secretKey + ciphertext as mac input * then THash convert to Mac hex string and return * @param secretKey derived key hex string * @param ciphertext encrypted hex string * @return mac as hex string */ function constructMac(secretKey, ciphertext) { let secretKeyBuf = utils_1.string2Buffer(secretKey); let ciphertextBuf = utils_1.string2Buffer(ciphertext); // concat buffer & THash let concated = Buffer.concat([secretKeyBuf, ciphertextBuf]); let hashedMac = THash_1.default(concated); return hashedMac.toString('hex'); } /** * construct base58 encoded string for CovenantSQL chain recover * privateKeyVersion(1B) + iv(16B) + ciphertext(48B) as concated hex * then base58 encoded the concated and return * @param privateKeyVersion 1 btye version * @param iv generated iv * @param ciphertext encrypted ciphertext * @return base58Encoded concated */ function constructEncrypted(privateKeyVersion, iv, ciphertext) { let versionBuf = Buffer.from([privateKeyVersion]); let ivBuf = utils_1.string2Buffer(iv); let ciphertextBuf = utils_1.string2Buffer(ciphertext); // concat buffer & base58 encode let concated = Buffer.concat([versionBuf, ivBuf, ciphertextBuf]); let base58Encoded = coinstring_1.default.encode(concated); return base58Encoded; } /** * deconstruct base58 encoded string for CovenantSQL chain recover * @param encrypted base58Encoded concated * @return { * privateKeyVersion 1 btye version * iv generated iv * ciphertext encrypted ciphertext * } */ function deconstructEncrypted(encrypted) { let encBuf = coinstring_1.default.decode(encrypted); // 1st byte as privateKeyVersion let versionBuf = encBuf.slice(0, 1); // next 16 bytes as iv let ivBuf = encBuf.slice(1, 17); // next 48 bytes as cipher let ciphertextBuf = encBuf.slice(17, 65); return { privateKeyVersion: versionBuf.toString('hex'), iv: ivBuf.toString('hex'), ciphertext: ciphertextBuf.toString('hex') }; } exports.deconstructEncrypted = deconstructEncrypted; //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoia2V5c3RvcmUuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi9zcmMvbGliL2tleXN0b3JlLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiI7Ozs7Ozs7Ozs7OztBQUFBLDREQUFtQztBQUNuQyxtQ0FBdUM7QUFDdkMsMERBQWlDO0FBRWpDLGlEQUFrQztBQUNsQyx1REFBd0M7QUFDeEMsdURBQXdDO0FBRXhDOzs7Ozs7O0dBT0c7QUFDSCxTQUFnQixjQUFjLENBQzVCLFFBQWdCLEVBQ2hCLElBQVksRUFDWixXQUFtQixFQUNuQixpQkFBeUI7SUFFekIsd0JBQXdCO0lBQ3hCLElBQUksTUFBTSxHQUFXLE1BQU0sQ0FBQyxnQkFBZ0IsRUFBRSxDQUFBO0lBQzlDLElBQUksTUFBTSxHQUFXLE1BQU0sQ0FBQyxxQkFBcUIsQ0FBQyxNQUFNLENBQUMsQ0FBQTtJQUN6RCxPQUFPLENBQUMsR0FBRyxDQUFDLGdDQUFnQyxFQUFHLE1BQU0sQ0FBQyxDQUFBO0lBRXRELG9CQUFvQjtJQUNwQixJQUFJLE9BQU8sR0FBVyxNQUFNLENBQUMsa0JBQWtCLENBQUMsTUFBTSxFQUFFLFdBQVcsQ0FBQyxDQUFBO0lBRXBFLGdDQUFnQztJQUNoQyxJQUFJLFNBQVMsR0FBVyxTQUFTLENBQUMsTUFBTSxDQUFDLFFBQVEsRUFBRSxJQUFJLENBQUMsQ0FBQTtJQUV4RCxzQ0FBc0M7SUFDdEMsSUFBSSxFQUFFLEdBQVcsU0FBUyxDQUFDLFVBQVUsRUFBRSxDQUFBO0lBQ3ZDLElBQUksVUFBVSxHQUFXLFNBQVMsQ0FBQyxPQUFPLENBQUMsTUFBTSxFQUFFLFNBQVMsRUFBRSxFQUFFLENBQUMsQ0FBQTtJQUVqRSxJQUFJLEdBQUcsR0FBVyxZQUFZLENBQUMsU0FBUyxFQUFFLFVBQVUsQ0FBQyxDQUFBO0lBQ3JELElBQUksUUFBUSxHQUFHLE9BQU8sQ0FBQyxPQUFPLEVBQUUsSUFBSSxFQUFFLEdBQUcsRUFBRSxVQUFVLEVBQUUsRUFBRSxFQUFFLGlCQUFpQixDQUFD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