async function _pbkdf2Passphrase(passphrase, salt) {
  if (window.crypto && window.crypto.subtle) {
    console.log('[crypt] Using native PBKDF2');

    const k = await window.crypto.subtle.importKey(
      'raw',
      Buffer.from(passphrase, 'utf8'),
      { name: 'PBKDF2' },
      false,
      ['deriveBits'],
    );

    const algo = {
      name: 'PBKDF2',
      salt: Buffer.from(salt, 'hex'),
      iterations: DEFAULT_PBKDF2_ITERATIONS,
      hash: 'SHA-256',
    };

    const derivedKeyRaw = await window.crypto.subtle.deriveBits(algo, k, DEFAULT_BYTE_LENGTH * 8);
    return Buffer.from(derivedKeyRaw).toString('hex');
  } else {
    console.log('[crypt] Using Forge PBKDF2');
    const derivedKeyRaw = forge.pkcs5.pbkdf2(
      passphrase,
      forge.util.hexToBytes(salt),
      DEFAULT_PBKDF2_ITERATIONS,
      DEFAULT_BYTE_LENGTH,
      forge.md.sha256.create(),
    );

    return forge.util.bytesToHex(derivedKeyRaw);
  }
}
async function _pbkdf2Passphrase(passphrase, salt) {
  if (window.crypto && window.crypto.subtle) {
    console.log('[crypt] Using native PBKDF2');

    const k = await window.crypto.subtle.importKey(
      'raw',
      Buffer.from(passphrase, 'utf8'),
      { name: 'PBKDF2' },
      false,
      ['deriveBits'],
    );

    const algo = {
      name: 'PBKDF2',
      salt: Buffer.from(salt, 'hex'),
      iterations: DEFAULT_PBKDF2_ITERATIONS,
      hash: 'SHA-256',
    };

    const derivedKeyRaw = await window.crypto.subtle.deriveBits(algo, k, DEFAULT_BYTE_LENGTH * 8);
    return Buffer.from(derivedKeyRaw).toString('hex');
  } else {
    console.log('[crypt] Using Forge PBKDF2');
    const derivedKeyRaw = forge.pkcs5.pbkdf2(
      passphrase,
      forge.util.hexToBytes(salt),
      DEFAULT_PBKDF2_ITERATIONS,
      DEFAULT_BYTE_LENGTH,
      forge.md.sha256.create(),
    );

    return forge.util.bytesToHex(derivedKeyRaw);
  }
}
async function _pbkdf2Passphrase ( passphrase , salt ) { if ( window . crypto && window . crypto . subtle ) { console . log ( '[crypt] Using native PBKDF2' ) ; const k = await window . crypto . subtle . importKey ( 'raw' , Buffer . from ( passphrase , 'utf8' ) , { name : 'PBKDF2' } , false , [ 'deriveBits' ] , ) ; const algo = { name : 'PBKDF2' , salt : Buffer . from ( salt , 'hex' ) , iterations : DEFAULT_PBKDF2_ITERATIONS , hash : 'SHA-256' , } ; const derivedKeyRaw = await window . crypto . subtle . deriveBits ( algo , k , DEFAULT_BYTE_LENGTH * 8 ) ; return Buffer . from ( derivedKeyRaw ) . toString ( 'hex' ) ; } else { console . log ( '[crypt] Using Forge PBKDF2' ) ; const derivedKeyRaw = forge . pkcs5 . pbkdf2 ( passphrase , forge . util . hexToBytes ( salt ) , DEFAULT_PBKDF2_ITERATIONS , DEFAULT_BYTE_LENGTH , forge . md . sha256 . create ( ) , ) ; return forge . util . bytesToHex ( derivedKeyRaw ) ; } }
Derive key from password

@param passphrase
@param salt hex representation of salt
Derive key from password
PBKDF2 - based implementation