diff --git a/src/index.ts b/src/index.ts index b425e8a..9b5bfc0 100644 --- a/src/index.ts +++ b/src/index.ts @@ -55,7 +55,7 @@ export async function encryptWithDetail( dataObj: R, salt = generateSalt(), ): Promise { - const key = await keyFromPassword(password, salt); + const key = await keyFromPassword(password, salt, true); const exportedKeyString = await exportKey(key); const vault = await encrypt(password, dataObj, key, salt); @@ -137,7 +137,7 @@ export async function decryptWithDetail( ): Promise { const payload = JSON.parse(text); const { salt } = payload; - const key = await keyFromPassword(password, salt); + const key = await keyFromPassword(password, salt, true); const exportedKeyString = await exportKey(key); const vault = await decrypt(password, text, key); @@ -216,11 +216,13 @@ export async function exportKey(key: CryptoKey): Promise { * * @param password - The password to use to generate key. * @param salt - The salt string to use in key derivation. + * @param exportable - Should the derived key be exportable. * @returns A CryptoKey for encryption and decryption. */ export async function keyFromPassword( password: string, salt: string, + exportable = false, ): Promise { const passBuffer = Buffer.from(password, STRING_ENCODING); const saltBuffer = Buffer.from(salt, 'base64'); @@ -242,7 +244,7 @@ export async function keyFromPassword( }, key, { name: DERIVED_KEY_FORMAT, length: 256 }, - true, + exportable, ['encrypt', 'decrypt'], ); diff --git a/test/index.spec.ts b/test/index.spec.ts index d86528c..db105c7 100644 --- a/test/index.spec.ts +++ b/test/index.spec.ts @@ -109,6 +109,7 @@ test('encryptor:encryptWithDetail returns vault', async ({ page }) => { { data, password }, ); expect(typeof encryptedDetail.vault).toBe('string'); + expect(typeof encryptedDetail.exportedKeyString).toBe('string'); }); test('encryptor:encrypt & decrypt with wrong password', async ({ page }) => { @@ -207,6 +208,9 @@ test('encryptor:decryptWithDetail returns same vault as decrypt', async ({ JSON.stringify(decryptWithDetailResult.vault), ); expect(Object.keys(decryptWithDetailResult).length).toBe(3); + expect(typeof decryptWithDetailResult.exportedKeyString).toStrictEqual( + 'string', + ); }); test('encryptor:encrypt using key then decrypt', async ({ page }) => { @@ -555,3 +559,30 @@ test('encryptor:encryptWithKey works with decryptWithKey', async ({ page }) => { JSON.stringify(newData), ); }); + +test('encryptor:keyFromPassword cannot be exported by default', async ({ + page, +}) => { + const password = 'a sample passw0rd'; + const data = { foo: 'data to encrypt' }; + const salt = await page.evaluate(() => window.encryptor.generateSalt()); + + const exportResult = await page.evaluate( + async (args) => { + const key = await window.encryptor.keyFromPassword( + args.password, + args.salt, + ); + + try { + const result = await window.encryptor.exportKey(key); + return result; + } catch (e) { + return 'error'; + } + }, + { data, password, salt }, + ); + + expect(exportResult).toStrictEqual('error'); +});